<!DOCTYPE html>
<html lang=zh>
<head>
    <meta charset="utf-8">
    
    <title>2-Corda数据结构 | johnny技术地</title>
    
    
        <meta name="keywords" content="DLT,Corda" />
    
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1" />
    <meta name="description" content="2-Corda数据结构StateThe project defines an IOUState in Java and Kotlin: JavaKotlin Copy 12345public class IOUState implements LinearState, QueryableState &amp;#123;    private final Integer value;    private">
<meta property="og:type" content="article">
<meta property="og:title" content="2-Corda数据结构">
<meta property="og:url" content="https://abcd_1101.gitee.io/gitee-internal-blog/2023/03/09/DLT/Ledger/Corda/2-Corda%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84/index.html">
<meta property="og:site_name" content="johnny技术地">
<meta property="og:description" content="2-Corda数据结构StateThe project defines an IOUState in Java and Kotlin: JavaKotlin Copy 12345public class IOUState implements LinearState, QueryableState &amp;#123;    private final Integer value;    private">
<meta property="og:locale">
<meta property="og:image" content="https://training.corda.net/getting-started/cdl_ioustate.png">
<meta property="og:image" content="https://training.corda.net/getting-started/command_hover_linear_state.png">
<meta property="og:image" content="https://training.corda.net/getting-started/linear_state_contract_state.png">
<meta property="og:image" content="https://training.corda.net/getting-started/has_implementations_button.png">
<meta property="og:image" content="https://training.corda.net/getting-started/has_implementations_hint.png">
<meta property="og:image" content="https://training.corda.net/getting-started/contract_state_implementations.png">
<meta property="og:image" content="https://training.corda.net/getting-started/cdl_iou_state_machine.png">
<meta property="og:image" content="https://training.corda.net/getting-started/command_data_implementations.png">
<meta property="og:image" content="https://training.corda.net/getting-started/cdl_iou_state_machine.png">
<meta property="og:image" content="https://training.corda.net/getting-started/contract_state_implementations.png">
<meta property="og:image" content="https://training.corda.net/getting-started/cdl_iou_state_evolution.png">
<meta property="og:image" content="https://training.corda.net/getting-started/cdl_create_iou_bpmn.png">
<meta property="og:image" content="c:/Users/51606/AppData/Roaming/Typora/typora-user-images/image-20221218221138953.png">
<meta property="og:image" content="https://training.corda.net/getting-started/notary_verifying_true_1.png">
<meta property="article:published_time" content="2023-03-09T09:20:59.000Z">
<meta property="article:modified_time" content="2023-04-22T04:21:05.796Z">
<meta property="article:author" content="Johnny">
<meta property="article:tag" content="DLT">
<meta property="article:tag" content="Corda">
<meta name="twitter:card" content="summary">
<meta name="twitter:image" content="https://training.corda.net/getting-started/cdl_ioustate.png">
    

    
        <link rel="alternate" href="/atom.xml" title="johnny技术地" type="application/atom+xml" />
    

    
        <link rel="icon" href="/gitee-internal-blog/favicon.ico" />
    

    
<link rel="stylesheet" href="/gitee-internal-blog/libs/font-awesome/css/font-awesome.min.css">

    
<link rel="stylesheet" href="/gitee-internal-blog/libs/open-sans/styles.css">

    
<link rel="stylesheet" href="/gitee-internal-blog/libs/source-code-pro/styles.css">


    
<link rel="stylesheet" href="/gitee-internal-blog/css/style.css">

    
<script src="/gitee-internal-blog/libs/jquery/2.1.3/jquery.min.js"></script>

    
<script src="/gitee-internal-blog/libs/jquery/plugins/cookie/1.4.1/jquery.cookie.js"></script>

    
    
        
<link rel="stylesheet" href="/gitee-internal-blog/libs/lightgallery/css/lightgallery.min.css">

    
    
        
<link rel="stylesheet" href="/gitee-internal-blog/libs/justified-gallery/justifiedGallery.min.css">

    
    
    
    


    
        <script async src="//busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js"></script>
    
<meta name="generator" content="Hexo 5.4.0"></head>

<body>
    <div id="container">
        <header id="header">
    <div id="header-main" class="header-inner">
        <div class="outer">
            <a href="/gitee-internal-blog/" id="logo">
                <i class="logo"></i>
                <span class="site-title">johnny技术地</span>
            </a>
            <nav id="main-nav">
                
                    <a class="main-nav-link" href="/gitee-internal-blog/">首页</a>
                
                    <a class="main-nav-link" href="/gitee-internal-blog/archives">归档</a>
                
                    <a class="main-nav-link" href="/gitee-internal-blog/categories">分类</a>
                
                    <a class="main-nav-link" href="/gitee-internal-blog/tags">标签</a>
                
                    <a class="main-nav-link" href="/gitee-internal-blog/about">关于</a>
                
            </nav>
            
            <div id="search-form-wrap">

    <form class="search-form">
        <input type="text" class="ins-search-input search-form-input" placeholder="Search" />
        <button type="submit" class="search-form-submit"></button>
    </form>
    <div class="ins-search">
    <div class="ins-search-mask"></div>
    <div class="ins-search-container">
        <div class="ins-input-wrapper">
            <input type="text" class="ins-search-input" placeholder="Type something..." />
            <span class="ins-close ins-selectable"><i class="fa fa-times-circle"></i></span>
        </div>
        <div class="ins-section-wrapper">
            <div class="ins-section-container"></div>
        </div>
    </div>
</div>
<script>
(function (window) {
    var INSIGHT_CONFIG = {
        TRANSLATION: {
            POSTS: 'Posts',
            PAGES: 'Pages',
            CATEGORIES: 'Categories',
            TAGS: 'Tags',
            UNTITLED: '(Untitled)',
        },
        ROOT_URL: '/gitee-internal-blog/',
        CONTENT_URL: '/gitee-internal-blog/content.json',
    };
    window.INSIGHT_CONFIG = INSIGHT_CONFIG;
})(window);
</script>

<script src="/gitee-internal-blog/js/insight.js"></script>


</div>
        </div>
    </div>
    <div id="main-nav-mobile" class="header-sub header-inner">
        <table class="menu outer">
            <tr>
                
                    <td><a class="main-nav-link" href="/gitee-internal-blog/">首页</a></td>
                
                    <td><a class="main-nav-link" href="/gitee-internal-blog/archives">归档</a></td>
                
                    <td><a class="main-nav-link" href="/gitee-internal-blog/categories">分类</a></td>
                
                    <td><a class="main-nav-link" href="/gitee-internal-blog/tags">标签</a></td>
                
                    <td><a class="main-nav-link" href="/gitee-internal-blog/about">关于</a></td>
                
                <td>
                    
    <div class="search-form">
        <input type="text" class="ins-search-input search-form-input" placeholder="Search" />
    </div>

                </td>
            </tr>
        </table>
    </div>
</header>

        <div class="outer">
            
            
                <aside id="sidebar">
   
        
    <div class="widget-wrap" id='categories'>
        <h3 class="widget-title">
            <span>categories</span>
            &nbsp;
            <a id='allExpand' href="#">
                <i class="fa fa-angle-double-down fa-2x"></i>
            </a>
        </h3>
        
        
        
         <ul class="unstyled" id="tree" > 
                    <li class="directory open">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder-open"></i>
                            &nbsp;
                            DLT
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory open">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder-open"></i>
                            &nbsp;
                            Ledger
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory open">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder-open"></i>
                            &nbsp;
                            Corda
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2023/03/09/DLT/Ledger/Corda/1-Corda%E4%BE%8B%E5%AD%90/">1-Corda例子</a></li>  <li class="file active"><a href="/gitee-internal-blog/2023/03/09/DLT/Ledger/Corda/2-Corda%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84/">2-Corda数据结构</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            SmartContract
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            DAML
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2023/02/04/DLT/SmartContract/DAML/1-Why%20Daml/">1-Why Daml</a></li>  <li class="file"><a href="/gitee-internal-blog/2023/02/04/DLT/SmartContract/DAML/2-Daml%20sample/">2-Daml sample</a></li>  <li class="file"><a href="/gitee-internal-blog/2023/04/22/DLT/SmartContract/DAML/3-Daml2%20Canton/">3-Daml2 Canton</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            概念和框架
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2023/02/04/DLT/%E6%A6%82%E5%BF%B5%E5%92%8C%E6%A1%86%E6%9E%B6/1-%E5%8C%BA%E5%9D%97%E9%93%BE%E7%90%86%E8%AE%BA%E5%9F%BA%E7%A1%80/">1-区块链理论基础</a></li>  <li class="file"><a href="/gitee-internal-blog/2023/02/04/DLT/%E6%A6%82%E5%BF%B5%E5%92%8C%E6%A1%86%E6%9E%B6/2-%E5%8C%BA%E5%9D%97%E9%93%BE%E7%9A%84%E6%8A%80%E6%9C%AF%E5%88%86%E6%9E%90%EF%BC%9A%E4%BB%A5%E5%A4%AA%E5%9D%8A%EF%BC%8CFabric%EF%BC%8CCorda/">2-区块链的技术分析：以太坊，Fabric，Corda</a></li>  <li class="file"><a href="/gitee-internal-blog/2023/02/04/DLT/%E6%A6%82%E5%BF%B5%E5%92%8C%E6%A1%86%E6%9E%B6/3-Blockchain101%20sharing/">3-Blockchain101 sharing</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            IDE
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/03/IDE-eclipse-debug-f5-8/">IDE eclipse debug f5-8</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            docker_k8s
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/19/docker_k8s/springcloud%20vs%20k8s/"></a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/docker_k8s/%E5%AE%B9%E5%99%A8-docker-k8s/">容器-docker-k8s</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            git
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/05/git-reset-and-revert/">git reset and revert</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/14/git-pull-request-to-contribute-other-project/">Pull request to contribute other project</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/18/git-stash%E7%94%A8%E6%B3%95/">git stash用法</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/16/git-tag%E8%AE%B0%E5%BD%95%E7%89%88%E6%9C%AC%E5%AF%B9%E5%BA%94commit/">git tag记录版本对应commit</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            java
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/25/java%E5%9F%BA%E7%A1%801/">java基础1</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            jvm
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            性能监测
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/11/jvisualvm%E5%92%8Csprintboot%20admin%E6%80%A7%E8%83%BD%E7%9B%91%E6%B5%8B/">jvisualvm和sprintboot admin性能监测</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            linux
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            常用命令
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/11/linux%E5%B8%B8%E7%94%A8%E5%91%BD%E4%BB%A4/">linux常用命令</a></li>  </ul> 
                    </li> 
                     <li class="file"><a href="/gitee-internal-blog/2021/04/18/linux-find%E5%91%BD%E4%BB%A4/">linux-find命令</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            spring
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/01/spring-log%E6%97%A5%E5%BF%97%E8%AE%B0%E5%BD%95/">日志记录</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/03/spring-mvc%E5%BF%85%E5%A4%87%E9%85%8D%E7%BD%AE/">spring mvc必备配置</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/23/spring%E8%84%9A%E6%89%8B%E6%9E%B6%E5%8E%9F%E7%90%86/">spring脚手架原理</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            windows
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/17/windows-dns%E6%9C%8D%E5%8A%A1%E5%99%A8%E6%9C%AA%E5%93%8D%E5%BA%94/">windows dns服务器未响应</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            中间件
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            mq
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/2-mq%E9%87%8D%E5%A4%8D%E9%A1%BA%E5%BA%8F%E6%B6%88%E8%B4%B9/">2-mq重复顺序消费</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/1-mq%E5%9F%BA%E7%A1%80/">1-mq基础</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/0-mq-zookeeper%E6%98%AF%E4%BB%80%E4%B9%88/">0-mq-zookeeper是什么</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/3-mq-kafka%E5%85%A5%E9%97%A8/">3-mq-kafka入门</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/4-mq%E9%97%AE%E9%A2%98%E4%B8%8D%E4%B8%A2%E5%A4%B1-%E9%87%8D%E5%A4%8D-%E6%9C%89%E5%BA%8F-%E5%A0%86%E7%A7%AF/">4-mq问题不丢失_重复_有序_堆积</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/05/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/5-mq-kafka-segement%E8%AF%BB%E5%86%99/">5-mq-kafka-segement读写</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/07/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/6-mq-kafka%E4%B8%89%E8%BF%9E%E5%87%BB/">6-mq-kafka三连击</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/12/%E4%B8%AD%E9%97%B4%E4%BB%B6/mq/7-mq-kafka%E6%98%AF%E6%8E%A8%E8%BF%98%E6%98%AF%E6%8B%89/">7-mq-kafka是推还是拉</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            必会框架
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E5%BF%85%E4%BC%9A%E6%A1%86%E6%9E%B6/%E6%A1%86%E6%9E%B6-%E9%AB%98%E6%80%A7%E8%83%BDNIO-Netty/">框架-高性能NIO-Netty</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            操作系统
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F-pageCache/">操作系统-pageCache</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F-nioFilechannel%E5%A0%86%E5%A4%96directBuffer%E4%B8%8E%E5%A0%86%E5%86%85byteBuffer/">操作系统-nioFilechannel堆外directBuffer与堆内byteBufferbyteBuffer</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F-%E8%AE%A1%E7%AE%97%E6%9C%BA%E7%BD%91%E7%BB%9C%E4%BC%98%E5%8C%96%E6%8F%A1%E6%89%8B%E6%8C%A5%E6%89%8B/">操作系统-计算机网络优化握手挥手</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F-%E8%AE%A1%E7%AE%97%E6%9C%BA%E7%BD%91%E7%BB%9C%E5%B8%B8%E9%97%AE/">操作系统-计算机网络常问</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F-%E8%AE%A1%E7%AE%97%E6%9C%BA%E7%BD%91%E7%BB%9C%E6%8A%93%E5%8C%85/">操作系统-计算机网络抓包</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            数据库
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            mysql
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/0-mysql%E7%BB%93%E6%9E%84%E4%B8%8E%E6%8F%92%E5%85%A5/">0-mysql结构与插入</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/1-mysql%E4%B8%80%E8%87%B4%E6%80%A7%E8%AF%BB-%E4%BA%8B%E5%8A%A1%E5%9B%9E%E6%BB%9A-mvcc/">1-mysql一致性读-事务回滚-mvcc</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/3-mysql-sql%E6%89%A7%E8%A1%8C%E8%BF%87%E7%A8%8B%E5%AE%8F%E8%A7%82%E6%B5%81%E7%A8%8B-redo-undo-bin/">3-mysql-sql执行过程宏观流程-redo-undo-bin</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/5-mysql-sql%E8%B0%83%E4%BC%98%E6%80%9D%E8%B7%AF/">5-mysql-sql调优思路</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/4-mysql-explain%E6%89%A7%E8%A1%8C%E5%85%B7%E4%BD%93%E6%B5%81%E7%A8%8B/">4-mysql-explain执行具体流程</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/6-mysql-%E7%B4%A2%E5%BC%95%E4%BD%9C%E7%94%A8%E5%92%8C%E8%AE%BE%E8%AE%A1/">6-mysql-索引作用和设计</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/8-mysql-%E6%95%B0%E6%8D%AE%E5%BA%93%E8%BF%9E%E6%8E%A5%E6%B1%A0%E8%AE%BE%E5%A4%9A%E5%A4%A7/">8-mysql-数据库连接池设多大</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/9-mysql-%E4%BB%8E%E4%B8%9A%E5%8A%A1%E5%88%B0%E6%95%B0%E6%8D%AE%E5%BA%93%E8%AE%BE%E8%AE%A1-%E8%BD%AF%E4%BB%B6%E5%B7%A5%E7%A8%8B/">9-mysql-从业务到数据库设计-软件工程</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/7-mysql-changebuffer-merge/">7-mysql-changebuffer-merge</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/2-mysql-undo-purge_bin_redo-flush%E8%84%8F%E9%A1%B5/">2-mysql-undo-purge_bin_redo-flush脏页</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/10-mysql-mysql8%E6%96%B0%E7%89%B9%E6%80%A7/">10-mysql-mysql8新特性</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/12-mysql-%E5%85%A8%E5%B1%80%E9%94%81-%E8%A1%A8%E9%94%81-%E8%A1%8C%E9%94%81/">12-mysql-全局锁-表锁-行锁</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/11-mysql-%E4%B8%BB%E4%BB%8E%E5%A4%8D%E5%88%B6%E5%92%8C%E5%AE%9E%E6%88%98/">11-mysql-主从复制和实战</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/13-mysql-%E6%9E%B6%E6%9E%84%E6%96%B9%E6%A1%88/">13-mysql-架构方案</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            redis
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/8-redis-%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84%E5%92%8C%E6%93%8D%E4%BD%9C/">8-redis-数据结构和操作</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/11-redis-%E5%8F%AF%E7%94%A8%E6%80%A7-mysql%E4%B8%80%E8%87%B4%E6%80%A7%E9%97%AE%E9%A2%98/">11-redis-可用性-mysql一致性问题</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/1-redis-%E5%A5%BD-%E4%BD%BF%E7%94%A8%E5%9C%BA%E6%99%AF/">1-redis-好-使用场景</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/2-redis-%E5%BF%AB-%E5%86%85%E5%AD%98%E8%80%97%E5%B0%BD%E5%90%8E%E4%BC%9A%E6%80%8E%E6%A0%B7/">2-redis-快-内存耗尽后会怎样</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/3-redis-%E5%BF%AB-%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84%E5%92%8C%E6%93%8D%E4%BD%9C/">3-redis-快-数据结构和操作</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/4-redis-%E5%BF%AB-%E4%B8%BA%E4%BD%95%E5%8F%98%E5%A4%9A%E7%BA%BF%E7%A8%8B/">4-redis-快-为何变多线程</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/7-redis-%E4%BC%98%E5%8C%96-%E6%9C%80%E4%BD%B3%E5%AE%9E%E8%B7%B5/"></a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/8-redis-%E4%BC%98%E5%8C%96-%E9%9B%AA%E5%B4%A9-%E7%A9%BF%E9%80%8F-%E5%87%BB%E7%A9%BF/">8-redis-优化-雪崩-穿透-击穿</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/9-redis-%E5%8F%AF%E7%94%A8%E6%80%A7-%E6%8C%81%E4%B9%85%E5%8C%96/">9-redis-可用性-持久化</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/20-redis-%E9%9D%A2%E8%AF%95%E9%A2%98/">20-redis-面试题</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/5-redis-%E5%BF%AB-%E5%A4%9A%E8%B7%AFio%E5%A4%8D%E7%94%A8/">5-redis-快-多路io复用</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/6-redis-%E4%BC%98%E5%8C%96-%E5%8F%98%E6%85%A2%E4%BA%86%E5%90%97/">6-redis-优化-变慢了吗</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E6%95%B0%E6%8D%AE%E5%BA%93/redis/10-redis-%E5%8F%AF%E7%94%A8%E6%80%A7-%E9%9B%86%E7%BE%A4%E7%AF%87/">10-redis-可用性-集群篇</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            知识点框架
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            19-数据库
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/08/02/19-1-Oracle%E5%B8%B8%E8%80%83/">19-1-Oracle常考</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            2-jvm
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/25/2-1-JVM%E8%84%91%E5%9B%BE/">2-1-JVM脑图</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/25/2-2-JVM%E5%86%85%E5%AD%98%E5%8C%BA%E5%9F%9F/">2-2-JVM内存区域</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/26/2-3-jvm%E8%BF%90%E8%A1%8C%E6%97%B6%E5%86%85%E5%AD%98/">2-3-jvm运行时内存</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/26/2-4-%E5%9E%83%E5%9C%BE%E5%9B%9E%E6%94%B6-%E7%AE%97%E6%B3%95-%E9%80%83%E9%80%B8%E5%88%86%E6%9E%90/">2-4-垃圾回收-算法-逃逸分析</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/27/2-5-java%E5%9B%9B%E7%A7%8D%E5%BC%95%E7%94%A8%E7%B1%BB%E5%9E%8B/">2-5-java四种引用类型</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/28/2-6-7-gc%E7%AE%97%E6%B3%95%E5%92%8C%E5%9E%83%E5%9C%BE%E6%94%B6%E9%9B%86%E5%99%A8/">2-6-7-gc算法和垃圾收集器</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/28/2-8-java-io-and-nio/">2-8-java io and nio</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/29/2-9-jvm%E7%B1%BB%E5%8A%A0%E8%BD%BD%E6%9C%BA%E5%88%B6/">2-9-jvm类加载机制</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            3-java集合
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/30/3-1-java%E6%8E%A5%E5%8F%A3%E7%BB%A7%E6%89%BF%E5%85%B3%E7%B3%BB%E4%B8%8E%E5%AE%9E%E7%8E%B0/">3-1-java接口继承关系与实现</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/30/3-2-List/">3-2-List</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/01/3-3-Set/">3-3-Set</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/01/3-4-Map%E6%98%A0%E5%B0%84/">3-4-Map映射</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            4-java多线程
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/07/02/4-1-2-%E5%A4%9A%E7%BA%BF%E7%A8%8B%E8%84%91%E5%9B%BE%E5%92%8C%E5%9B%9B%E7%A7%8D%E7%BA%BF%E7%A8%8B%E5%88%9B%E5%BB%BA%E6%96%B9%E6%B3%95/">4-1-2-多线程脑图和四种线程创建</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/02/4-3-4%E7%A7%8D%E7%BA%BF%E7%A8%8B%E6%B1%A0/">4-3-4种线程池</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/02/4-4-%E7%BA%BF%E7%A8%8B%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F5%E7%A7%8D%E7%8A%B6%E6%80%81/">4-4-线程生命周期5种状态</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/02/4-5-%E7%BB%88%E6%AD%A2%E7%BA%BF%E7%A8%8B4%E6%96%B9%E5%BC%8F/">4-5-终止线程4方式</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/02/4-6-7-sleep%E4%B8%8Ewait-start%E4%B8%8Erun/">4-6-7-sleep与wait-start与run</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/03/4-8-java%E5%90%8E%E5%8F%B0%E7%BA%BF%E7%A8%8B/">4-8-java后台线程</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/03/4-9-java%E9%94%81/">4-9-java锁</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/05/4-10-%E7%BA%BF%E7%A8%8B%E5%9F%BA%E6%9C%AC%E6%96%B9%E6%B3%95/">4-10-线程基本方法</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/06/4-11-%E7%BA%BF%E7%A8%8B%E4%B8%8A%E4%B8%8B%E6%96%87%E5%88%87%E6%8D%A2/">4-11-线程上下文切换</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/06/4-12-%E5%90%8C%E6%AD%A5%E9%94%81%E4%B8%8E%E6%AD%BB%E9%94%81/">4-12-同步锁与死锁</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/06/4-13-%E7%BA%BF%E7%A8%8B%E6%B1%A0%E5%8E%9F%E7%90%86/">4-13-线程池原理</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/08/4-14-%E9%98%BB%E5%A1%9E%E9%98%9F%E5%88%97/">4-14-阻塞队列</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/10/4-15-cyclicBarrier-countdownlatch-semaphore/">4-15-cyclicBarrier-countdownlatch-semaphore</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/14/4-16-volatile%E5%85%B3%E9%94%AE%E5%AD%97%E4%BD%9C%E7%94%A8/">4-16-volatile关键字作用</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/14/4-17-%E4%B8%A4%E4%B8%AA%E7%BA%BF%E7%A8%8B%E5%85%B1%E4%BA%AB%E6%95%B0%E6%8D%AE/">4-17-两个线程共享数据</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/16/4-18-ThreadLocal%E4%BD%9C%E7%94%A8/">4-18-ThreadLocal作用</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/16/4-19-synchronized%E5%92%8Creentrantlock%E5%8C%BA%E5%88%AB/">4-19-synchronized和reentrantlock区别</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/17/4-20-ConcurrentHashMap/">4-20-ConcurrentHashMap</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/17/4-21-22-java%E7%BA%BF%E7%A8%8B%E8%B0%83%E5%BA%A6%E5%92%8C%E7%AE%97%E6%B3%95/">4-21-22-java线程调度和算法</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/17/4-23-cas%E6%AF%94%E8%BE%83%E5%B9%B6%E4%BA%A4%E6%8D%A2/">4-23-cas比较并交换</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/17/4-24-aqs%E6%8A%BD%E8%B1%A1%E7%9A%84%E9%98%9F%E5%88%97%E5%90%8C%E6%AD%A5%E5%99%A8/">4-24-aqs抽象的队列同步器</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            5-java基础
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/07/19/5-1-exception%E5%BC%82%E5%B8%B8%E5%88%86%E7%B1%BB%E5%8F%8A%E5%A4%84%E7%90%86/">5-1-exception异常分类及处理</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/20/5-2-java%E5%8F%8D%E5%B0%84/">5-2-java反射</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/22/5-3-java%E6%B3%A8%E8%A7%A3annotation/">5-3-java注解annotation</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/24/5-4-java%E5%86%85%E9%83%A8%E7%B1%BB/">5-4-java内部类</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/14/5-5-jdk8-lambda/">5-5-jdk8-lambda</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/14/5-6-RxJava/">5-6-RxJava</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/14/5-7-java-Observer%E6%8E%A5%E5%8F%A3%E5%92%8CObservable%E7%B1%BB/">5-7-java-Observer接口和Observable类</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            6-spring
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/03/6-2-springboot%E5%B8%B8%E8%80%83/">6-2-springboot常考</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/31/6-1-spring%E5%B8%B8%E8%80%83/">6-1-spring常考</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/28/6-3-springcloud%E7%94%A8%E8%BF%87%E7%9A%84/">6-3-springcloud用过的</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            面试的项目实现
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            中间件
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            es
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E4%B8%AD%E9%97%B4%E4%BB%B6/es/es/">es</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            微服务
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/08/21/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/%E5%BE%AE%E6%9C%8D%E5%8A%A1/hystrix/"></a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            数据库
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            mysql
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/09/04/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/%E6%95%B0%E6%8D%AE%E5%BA%93/mysql/0-mysql%E7%BB%93%E6%9E%84%E4%B8%8E%E6%8F%92%E5%85%A5/">0-mysql结构与插入</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            自动补全
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/%E8%87%AA%E5%8A%A8%E8%A1%A5%E5%85%A8/es%E8%87%AA%E5%8A%A8%E8%A1%A5%E5%85%A8/">es自动补全</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/21/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/%E8%87%AA%E5%8A%A8%E8%A1%A5%E5%85%A8/redis%E8%87%AA%E5%8A%A8%E8%A1%A5%E5%85%A8/"></a></li>  </ul> 
                    </li> 
                     <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/IJP%E9%9D%A2%E8%AF%95%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/">IJP面试项目实现</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E7%9A%84%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/Ex%E9%9D%A2%E8%AF%95%E9%A1%B9%E7%9B%AE%E5%AE%9E%E7%8E%B0/">Ex面试项目实现</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            面试题
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E9%A2%98/SpringBoot+Tomcat+Nginx+Netty%E9%9D%A2%E8%AF%95%E9%A2%98/">SpringBoot+Tomcat+Nginx+Netty面试题</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E9%A2%98/%E9%98%BF%E9%87%8C%E9%9D%A2%E8%AF%95%E4%BA%8C/">阿里面试题2</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/06/25/%E9%9D%A2%E8%AF%95%E9%A2%98/%E9%98%BF%E9%87%8C%E9%9D%A2%E8%AF%95%E4%B8%80/">阿里面试题1</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/16/%E9%9D%A2%E8%AF%95%E9%A2%98-java%E5%9F%BA%E7%A1%80%E9%9D%A2%E8%AF%9516%E9%97%AE/">面试题-java基础面试16问</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            项目经历
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            2019
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            xinge_notification
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/05/oracle_explain/">Oracle explain</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            2021
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            房贷项目
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/05/%E9%A1%B9%E7%9B%AE%E4%BB%8E0%E5%88%B01/">项目从0到1</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/12/email-telnet-smtp-health-check/">email telnet smtp health check</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/12/%E5%8E%8B%E6%B5%8B%E5%8F%82%E6%95%B0%E6%8C%87%E6%A0%87/">压测参数指标</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/12/checkmarx%E5%AE%89%E5%85%A8%E6%89%AB%E6%8F%8F/">checkmarx安全扫描</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/25/db-table-annotation/">db table annotation</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/04/25/jdbctemplate-sql-injection/">jdbctemplate sql injection</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            微信开发
                        </a>
                         <ul class="unstyled" id="tree" > 
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            安全
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/16/%E5%AE%89%E5%85%A8-java-ssl%E9%94%99%E8%AF%AF%E8%A7%A3%E5%86%B3%E7%A5%9E%E5%99%A8-net-debug%E5%8F%82%E6%95%B0/">安全-java ssl 错误解决神器 net debug参数</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/28/%E5%AE%89%E5%85%A8-%E5%8A%A0%E5%AF%86%E6%9C%BA/">安全-加密机</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            容器
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/07/28/%E6%9C%8D%E5%8A%A1%E5%99%A8/%E6%9C%8D%E5%8A%A1%E5%99%A8-IBM%20websphere%E7%BB%8F%E9%AA%8C%20-%20%E5%89%AF%E6%9C%AC/">服务器-IBM websphere经验</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/28/%E6%9C%8D%E5%8A%A1%E5%99%A8/%E6%9C%8D%E5%8A%A1%E5%99%A8-Tomcat%E7%BB%8F%E9%AA%8C/">服务器-Tomcat经验</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/07/28/%E6%9C%8D%E5%8A%A1%E5%99%A8/%E6%9C%8D%E5%8A%A1%E5%99%A8-IBM%20websphere%E7%BB%8F%E9%AA%8C/">服务器-IBM websphere经验</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/15/docker_k8s/%E5%AE%B9%E5%99%A8-k8s%E7%BD%91%E9%A1%B5%E5%B8%B8%E8%A7%81%E5%90%8D%E8%AF%8D/">容器-k8s网页常见名词</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/09/06/docker_k8s/%E5%AE%B9%E5%99%A8-Istio/">容器-Istio</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            小程序
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/16/%E5%BE%AE%E4%BF%A1%E5%B0%8F%E7%A8%8B%E5%BA%8FnavigateTo%E4%B8%8EredirectTo%E5%8C%BA%E5%88%AB/">小程序navigateTo与redirectTo区别</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/08/30/%E5%BE%AE%E4%BF%A1%E5%B0%8F%E7%A8%8B%E5%BA%8F%E7%9A%84%E9%85%8D%E7%BD%AE/">微信小程序的配置</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            手机抓包
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/04/10/Fiddler%E5%AF%B9%E5%AE%89%E5%8D%93%E7%A7%BB%E5%8A%A8%E7%AB%AF%E7%9A%84%E6%8A%93%E5%8C%85%E6%B5%8B%E8%AF%95/">Fiddler对安卓移动端的抓包测试</a></li>  </ul> 
                    </li> 
                    
                    <li class="directory">
                        <a href="#" data-role="directory">
                            <i class="fa fa-folder"></i>
                            &nbsp;
                            高级群发系统
                        </a>
                         <ul class="unstyled" id="tree" >  <li class="file"><a href="/gitee-internal-blog/2021/05/09/Oracle-clob%E5%AD%97%E6%AE%B5/">Oracle clob字段</a></li>  </ul> 
                    </li> 
                     <li class="file"><a href="/gitee-internal-blog/2021/04/18/%E9%A1%B9%E7%9B%AE%E6%80%A7%E8%83%BD%E5%8F%82%E6%95%B0/">项目性能参数</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/09/%E5%BE%AE%E4%BF%A1%E6%8E%A5%E5%8F%A3%E6%B3%A8%E6%84%8F%E7%82%B9%E6%B1%87%E9%9B%86/">微信接口注意点汇集</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/09/%E5%BE%AE%E4%BF%A1%E4%B8%93%E7%BA%BF%E7%9A%84%E7%BD%91%E7%BB%9C%E5%B1%82%E7%90%86%E8%A7%A3/">专线的网络层理解</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/15/%E5%BE%AE%E4%BF%A1Sprint-plan/">Sprint plan</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/15/%E5%BE%AE%E4%BF%A1%E4%B8%8E%E9%93%B6%E8%81%94%E7%9A%84sso%E5%8D%95%E7%82%B9%E7%99%BB%E5%BD%95/">微信与银联的sso单点登录</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/22/G3%E8%87%AA%E5%8A%A8%E5%8C%96/">G3自动化</a></li>  <li class="file"><a href="/gitee-internal-blog/2021/05/29/%E5%BE%AE%E4%BF%A1%E9%A1%B9%E7%9B%AE%E5%BE%80ikp%E6%90%AC/">微信项目往ikp搬</a></li>  </ul> 
                    </li> 
                     </ul> 
                    </li> 
                     </ul> 
    </div>
    <script>
        $(document).ready(function() {
            var iconFolderOpenClass  = 'fa-folder-open';
            var iconFolderCloseClass = 'fa-folder';
            var iconAllExpandClass = 'fa-angle-double-down';
            var iconAllPackClass = 'fa-angle-double-up';
            // Handle directory-tree expansion:
            // 左键单独展开目录
            $(document).on('click', '#categories a[data-role="directory"]', function (event) {
                event.preventDefault();

                var icon = $(this).children('.fa');
                var expanded = icon.hasClass(iconFolderOpenClass);
                var subtree = $(this).siblings('ul');
                icon.removeClass(iconFolderOpenClass).removeClass(iconFolderCloseClass);
                if (expanded) {
                    if (typeof subtree != 'undefined') {
                        subtree.slideUp({ duration: 100 });
                    }
                    icon.addClass(iconFolderCloseClass);
                } else {
                    if (typeof subtree != 'undefined') {
                        subtree.slideDown({ duration: 100 });
                    }
                    icon.addClass(iconFolderOpenClass);
                }
            });
            // 右键展开下属所有目录
            $('#categories a[data-role="directory"]').bind("contextmenu", function(event){
                event.preventDefault();
                
                var icon = $(this).children('.fa');
                var expanded = icon.hasClass(iconFolderOpenClass);
                var listNode = $(this).siblings('ul');
                var subtrees = $.merge(listNode.find('li ul'), listNode);
                var icons = $.merge(listNode.find('.fa'), icon);
                icons.removeClass(iconFolderOpenClass).removeClass(iconFolderCloseClass);
                if(expanded) {
                    subtrees.slideUp({ duration: 100 });
                    icons.addClass(iconFolderCloseClass);
                } else {
                    subtrees.slideDown({ duration: 100 });
                    icons.addClass(iconFolderOpenClass);
                }
            })
            // 展开关闭所有目录按钮
            $(document).on('click', '#allExpand', function (event) {
                event.preventDefault();
                
                var icon = $(this).children('.fa');
                var expanded = icon.hasClass(iconAllExpandClass);
                icon.removeClass(iconAllExpandClass).removeClass(iconAllPackClass);
                if(expanded) {
                    $('#sidebar .fa.fa-folder').removeClass('fa-folder').addClass('fa-folder-open')
                    $('#categories li ul').slideDown({ duration: 100 });
                    icon.addClass(iconAllPackClass);
                } else {
                    $('#sidebar .fa.fa-folder-open').removeClass('fa-folder-open').addClass('fa-folder')
                    $('#categories li ul').slideUp({ duration: 100 });
                    icon.addClass(iconAllExpandClass);
                }
            });  
        });
    </script>

    
    <div id="toTop" class="fa fa-angle-up"></div>
</aside>
            
            <section id="main"><article id="post-DLT/Ledger/Corda/2-Corda数据结构" class="article article-type-post" itemscope itemprop="blogPost">
    <div class="article-inner">
        
        
            <header class="article-header">
                
                    <div class="article-meta">
                        
    <div class="article-category">
    	<i class="fa fa-folder"></i>
        <a class="article-category-link" href="/gitee-internal-blog/categories/DLT/">DLT</a><i class="fa fa-angle-right"></i><a class="article-category-link" href="/gitee-internal-blog/categories/DLT/Ledger/">Ledger</a><i class="fa fa-angle-right"></i><a class="article-category-link" href="/gitee-internal-blog/categories/DLT/Ledger/Corda/">Corda</a>
    </div>

                        
    <div class="article-tag">
        <i class="fa fa-tag"></i>
        <a class="tag-link-link" href="/gitee-internal-blog/tags/Corda/" rel="tag">Corda</a>, <a class="tag-link-link" href="/gitee-internal-blog/tags/DLT/" rel="tag">DLT</a>
    </div>

                        
    <div class="article-date">
        <i class="fa fa-calendar"></i>
        <a href="/gitee-internal-blog/2023/03/09/DLT/Ledger/Corda/2-Corda%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84/">
            <time datetime="2023-03-09T09:20:59.000Z" itemprop="datePublished">2023-03-09</time>
        </a>
    </div>


                        
                            <i class="fa fa-bar-chart"></i>
                            <span id="busuanzi_container_site_pv"><span id="busuanzi_value_page_pv"></span></span>    
                        
                        
                            <div class="article-meta-button">
                                <a target="_blank" rel="noopener" href='https://github.com/zthxxx/Wiki-site/raw/writing/source/_posts/DLT/Ledger/Corda/2-Corda数据结构.md'> Source </a>
                            </div>
                            <div class="article-meta-button">
                                <a target="_blank" rel="noopener" href='https://github.com/zthxxx/Wiki-site/edit/writing/source/_posts/DLT/Ledger/Corda/2-Corda数据结构.md'> Edit </a>
                            </div>
                            <div class="article-meta-button">
                                <a target="_blank" rel="noopener" href='https://github.com/zthxxx/Wiki-site/commits/writing/source/_posts/DLT/Ledger/Corda/2-Corda数据结构.md'> History </a>
                            </div>
                        
                    </div>
                
                
    
        <h1 class="article-title" itemprop="name">
            2-Corda数据结构
        </h1>
    

            </header>
        
        
        <div class="article-entry" itemprop="articleBody">
        
        
            
                <div id="toc" class="toc-article">
                <strong class="toc-title">Catalogue</strong>
                    <ol class="toc"><li class="toc-item toc-level-1"><a class="toc-link" href="#2-Corda%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84"><span class="toc-number">1.</span> <span class="toc-text">2-Corda数据结构</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#State"><span class="toc-number">1.0.1.</span> <span class="toc-text">State</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#The-Parties"><span class="toc-number">1.0.1.1.</span> <span class="toc-text">The Parties</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#Value"><span class="toc-number">1.0.1.2.</span> <span class="toc-text">Value</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#Linear-Id"><span class="toc-number">1.0.1.3.</span> <span class="toc-text">Linear Id</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#Schema"><span class="toc-number">1.0.1.4.</span> <span class="toc-text">Schema</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Contract"><span class="toc-number">1.0.2.</span> <span class="toc-text">Contract</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#Command"><span class="toc-number">1.0.2.1.</span> <span class="toc-text">Command</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#Verify"><span class="toc-number">1.0.2.2.</span> <span class="toc-text">Verify</span></a><ol class="toc-child"><li class="toc-item toc-level-5"><a class="toc-link" href="#requireSingleCommand"><span class="toc-number">1.0.2.2.1.</span> <span class="toc-text">requireSingleCommand</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#ContractsDSL"><span class="toc-number">1.0.2.2.2.</span> <span class="toc-text">ContractsDSL</span></a></li><li class="toc-item toc-level-5"><a class="toc-link" href="#Other-points"><span class="toc-number">1.0.2.2.3.</span> <span class="toc-text">Other points</span></a></li></ol></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Flow"><span class="toc-number">1.0.3.</span> <span class="toc-text">Flow</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#About-the-Flows"><span class="toc-number">1.0.3.1.</span> <span class="toc-text">About the Flows</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#ExampleFlow-Initiator-flow"><span class="toc-number">1.0.3.2.</span> <span class="toc-text">ExampleFlow.Initiator flow</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#ExampleFlow-Acceptor-flow"><span class="toc-number">1.0.3.3.</span> <span class="toc-text">ExampleFlow.Acceptor flow</span></a></li></ol></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#look-into-DB"><span class="toc-number">1.1.</span> <span class="toc-text">look into DB</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#Create-your-second-IOU"><span class="toc-number">1.1.1.</span> <span class="toc-text">Create your second IOU</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#PartyA%E2%80%99s-H2-browser-tab"><span class="toc-number">1.1.1.1.</span> <span class="toc-text">PartyA’s H2 browser tab</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Confirm-your-IOU"><span class="toc-number">1.1.2.</span> <span class="toc-text">Confirm your IOU</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#more-command"><span class="toc-number">1.1.3.</span> <span class="toc-text">more command</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Create-your-third-IOU"><span class="toc-number">1.1.4.</span> <span class="toc-text">Create your third IOU</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#No-Notary-validate"><span class="toc-number">1.2.</span> <span class="toc-text">No Notary validate</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%85%B3%E4%BA%8Eresponder%E7%B1%BB"><span class="toc-number">1.3.</span> <span class="toc-text">关于responder类</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#Initiator"><span class="toc-number">1.3.1.</span> <span class="toc-text">Initiator</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#The-class-declaration"><span class="toc-number">1.3.1.1.</span> <span class="toc-text">The class declaration</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#The-fields"><span class="toc-number">1.3.1.2.</span> <span class="toc-text">The fields</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#The-constructors"><span class="toc-number">1.3.1.3.</span> <span class="toc-text">The constructors</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#call"><span class="toc-number">1.3.1.4.</span> <span class="toc-text">call</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#Finalisation"><span class="toc-number">1.3.1.5.</span> <span class="toc-text">Finalisation</span></a></li></ol></li><li class="toc-item toc-level-3"><a class="toc-link" href="#Responder"><span class="toc-number">1.3.2.</span> <span class="toc-text">Responder</span></a><ol class="toc-child"><li class="toc-item toc-level-4"><a class="toc-link" href="#The-class-declaration-1"><span class="toc-number">1.3.2.1.</span> <span class="toc-text">The class declaration</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#The-field"><span class="toc-number">1.3.2.2.</span> <span class="toc-text">The field</span></a></li><li class="toc-item toc-level-4"><a class="toc-link" href="#The-constructor"><span class="toc-number">1.3.2.3.</span> <span class="toc-text">The constructor</span></a></li></ol></li></ol></li></ol></li></ol>
                </div>
            
        
        
            <h1 id="2-Corda数据结构"><a href="#2-Corda数据结构" class="headerlink" title="2-Corda数据结构"></a>2-Corda数据结构</h1><h3 id="State"><a href="#State" class="headerlink" title="State"></a>State</h3><p>The project defines an IOUState in <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/state/IOUState.java#L23-L27">Java</a> and <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-kotlin/src/main/kotlin/com/example/state/IOUState.kt#L25-L29">Kotlin</a>:</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">IOUState</span> <span class="keyword">implements</span> <span class="title">LinearState</span>, <span class="title">QueryableState</span> </span>&#123;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> Integer value;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> Party lender;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> Party borrower;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> UniqueIdentifier linearId;</span><br></pre></td></tr></table></figure>



<p><img src="https://training.corda.net/getting-started/cdl_ioustate.png" alt="IOU State as a diagram"></p>
<p>In case it is not clear, IOU is short for “I owe you (money)”. The IOUs in this example have four properties:</p>
<ul>
<li>2 parties: <code>lender</code> and <code>borrower</code>,</li>
<li>1 <code>value</code>,</li>
<li>and 1 <code>id</code>.</li>
</ul>
<h4 id="The-Parties"><a href="#The-Parties" class="headerlink" title="The Parties"></a>The Parties</h4><p>Let us take a quick look at the parties.</p>
<ul>
<li><p><code>Party</code>: Both <code>lender</code> and <code>borrower</code> are of type <code>Party</code>. If you look at <code>Party</code>’s definition, it starts to get a bit cryptic, with its <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/identity/Party.kt#L38">default constructor</a>. In essence, it is a pair made of:</p>
<ol>
<li>a <code>CordaX500Name</code>, a.k.a. a name,</li>
<li>and a <code>PublicKey</code> interface.</li>
</ol>
<p>Copy</p>
<figure class="highlight kotlin"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Party</span></span>(<span class="keyword">val</span> name: CordaX500Name, owningKey: PublicKey) : Destination, AbstractParty(owningKey) &#123;`</span><br></pre></td></tr></table></figure></li>
<li><p><code>CordaX500Name</code>: If you follow again inside <code>CordaX500Name</code>, you will see <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/identity/CordaX500Name.kt#L31">here</a> that it identifies the legal name of an entity (e.g <code>&quot;CN=Alice Corp,O=Alice Corp,L=London,C=GB&quot;</code>). For now, let’s not dig any further.</p>
<p>Copy</p>
<figure class="highlight kotlin"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">data</span> <span class="class"><span class="keyword">class</span> <span class="title">CordaX500Name</span></span>(<span class="keyword">val</span> commonName: String?,</span><br><span class="line">                         <span class="keyword">val</span> organisationUnit: String?,</span><br><span class="line">                         <span class="keyword">val</span> organisation: String,</span><br><span class="line">                         <span class="keyword">val</span> locality: String,</span><br><span class="line">                         <span class="keyword">val</span> state: String?,</span><br><span class="line">                         <span class="keyword">val</span> country: String) &#123;</span><br></pre></td></tr></table></figure></li>
<li><p><code>AbstractParty</code>: That is <code>Party</code>’s parent class and it is interesting to notice its <code>@CordaSerializable</code> <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/identity/AbstractParty.kt#L14">annotation</a>, which makes sense because this is information that will be exchanged between nodes.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@CordaSerializable</span></span><br></pre></td></tr></table></figure></li>
</ul>
<h4 id="Value"><a href="#Value" class="headerlink" title="Value"></a>Value</h4><p>Back to <code>IOUState</code>.</p>
<p>Little is said about <code>value</code> other than it is an <code>Integer</code>. What is not said is noteworthy. It is not limited to positive values. This constraint will be found elsewhere. This was a design decision on the part of the Corda team, in order to organize constraints in one place rather than having them scattered across various constructors.</p>
<h4 id="Linear-Id"><a href="#Linear-Id" class="headerlink" title="Linear Id"></a>Linear Id</h4><p>For <code>IOUState</code> to be usable as a state on the ledger, it would have sufficed for it to implement <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/ContractState.kt#L16-L17"><code>ContractState</code></a>, which, you will notice is also <code>@CordaSerializable</code>. However, so as not for us to reinvent the wheel, the Corda team has already prepared a number of implementations that can assist us with simple cases. These are part of the list of things that R3 is doing to increase the productivity of developers. To see a list of implementations of <code>ContractState</code> in IntelliJ:</p>
<ol>
<li><p>Open <code>IOUState</code>.</p>
</li>
<li><p>Command-Click or Control-Click on <code>LinearState</code>:</p>
<p><img src="https://training.corda.net/getting-started/command_hover_linear_state.png" alt="Command hover LinearState"></p>
</li>
<li><p>It opens <code>LinearState</code>. Same here, you Command-Click on <code>ContractState</code>:</p>
<p><img src="https://training.corda.net/getting-started/linear_state_contract_state.png" alt="LinearState declaration"></p>
</li>
<li><p>It opens <code>ContractState</code>, then on the left, click the small green <code>I</code>:</p>
<p><img src="https://training.corda.net/getting-started/has_implementations_button.png" alt="Has implementations button"></p>
<p><img src="https://training.corda.net/getting-started/has_implementations_hint.png" alt="Has implementations hint"></p>
</li>
<li><p>You get a drop-down of implementations:</p>
<p><img src="https://training.corda.net/getting-started/contract_state_implementations.png" alt="ContractState Implementations"></p>
</li>
</ol>
<p>In this example, the team chose <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/Structures.kt#L128"><code>interface LinearState</code></a>, which offers a rudimentary way to identify successor states by way of the <em>linear id</em>. This linear id is meant to be unique. So when you use <code>LinearState</code>, it is incumbent on you, the developer, to make sure that you do not have 2 unconsumed states with the same linear id at any point in time. It is also incumbent on you to make sure that successor states have the same linear id as the states they replace. Doing otherwise defeats the purpose of <code>LinearState</code>.</p>
<h4 id="Schema"><a href="#Schema" class="headerlink" title="Schema"></a>Schema</h4><p>States can be persisted in node vaults by various methods:</p>
<ol>
<li>Embedded in a known transaction. This is unavoidable if the node receives a signed transaction and saves it to transaction storage. An output state is part of the serialized blob of the transaction in any case. For this reason, when a node receives a transaction you can consider that its output states have been <em>disclosed</em>.</li>
<li>Stored as a discrete state. This is automatically done by the node when it receives a transaction that mentions one of its public keys as a participant. Presumably, the node, its owners or its customers are meant to retrieve and use it.</li>
<li>Stored as a row in a custom SQL table in the node’s vault. This is done explicitly by the CorDapp’s developer. Doing so enables the option of running complex queries on known states.</li>
</ol>
<p>Understand that:</p>
<ul>
<li>When it is stored in fashion 3, a state is also stored in fashion 2.</li>
<li>And, when it is stored in fashion 2, it is also stored in fashion 1.</li>
</ul>
<p>As a matter of fact, for this project, a decision was made to save <code>IOUState</code>s in their own custom vault table. This is not a necessity but this example is meant to show you methods that are available to you. To achieve it, all that had to be done was to declare that <code>IOUState</code> as a <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/state/IOUState.java#L23"><code>QueryableState</code></a> and specify the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/state/IOUState.java#L53-L67">ORM model</a> to use.</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">IOUState</span> <span class="keyword">implements</span> <span class="title">LinearState</span>, <span class="title">QueryableState</span> </span>&#123;</span><br></pre></td></tr></table></figure>

<p>and the necessary implementation:</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Override</span> <span class="function"><span class="keyword">public</span> PersistentState <span class="title">generateMappedObject</span><span class="params">(MappedSchema schema)</span> </span>&#123;</span><br><span class="line">    <span class="keyword">if</span> (schema <span class="keyword">instanceof</span> IOUSchemaV1) &#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="keyword">new</span> IOUSchemaV1.PersistentIOU(</span><br><span class="line">                <span class="keyword">this</span>.lender.getName().toString(),</span><br><span class="line">                <span class="keyword">this</span>.borrower.getName().toString(),</span><br><span class="line">                <span class="keyword">this</span>.value,</span><br><span class="line">                <span class="keyword">this</span>.linearId.getId());</span><br><span class="line">    &#125; <span class="keyword">else</span> &#123;</span><br><span class="line">        <span class="keyword">throw</span> <span class="keyword">new</span> IllegalArgumentException(<span class="string">&quot;Unrecognized schema $schema&quot;</span>);</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>Moving on.</p>
<h3 id="Contract"><a href="#Contract" class="headerlink" title="Contract"></a>Contract</h3><p>The contract will ensure that an <code>IOUState</code> will transition as per the following state machine view:</p>
<p><img src="https://training.corda.net/getting-started/cdl_iou_state_machine.png" alt="IOU State Machine View"></p>
<p>Where SC: is short for Signing Constraints.</p>
<p>The project defines an <code>IOUContract</code> in <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L27">Java</a> and in <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-kotlin/src/main/kotlin/com/example/contract/IOUContract.kt#L22">Kotlin</a>. For it to be usable on the ledger as a contract, it has to implement the <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/Structures.kt#L254-L265"><code>Contract</code></a> interface:</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">IOUContract</span> <span class="keyword">implements</span> <span class="title">Contract</span> </span>&#123;</span><br></pre></td></tr></table></figure>

<p>Notice how <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L28"><code>IOUContract.ID</code></a> repeats information about itself - its fully qualified name. When you build a transaction and add a state to it, you will associate a contract to a state by way of this fully qualified name. If you are so inclined, you can use some reflection instead:</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">final</span> String ID = IOUContract.class.getCanonicalName();</span><br></pre></td></tr></table></figure>

<h4 id="Command"><a href="#Command" class="headerlink" title="Command"></a>Command</h4><p>Remember that commands define intent. The only command available in this project is <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L61"><code>Create</code></a>. It could have been defined anywhere. The design decision was to encapsulate it inside <code>IOUContract</code>. Once more, if you Command-Click to <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/Structures.kt#L196-L197"><code>CommandData</code></a>, notice how it is <code>@CordaSerializable</code> as this will also be serialized as part of the transaction.</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">Commands</span> <span class="keyword">extends</span> <span class="title">CommandData</span> </span>&#123;</span><br><span class="line">    <span class="class"><span class="keyword">class</span> <span class="title">Create</span> <span class="keyword">implements</span> <span class="title">Commands</span> </span>&#123;&#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>These nested classes are merely marker interfaces in this instance, marker in the sense that they do not declare any function. They can also declare fields, as you shall see in later chapters. As with states, the Corda team has created further command implementations (Click on the green I on the left):</p>
<p><img src="https://training.corda.net/getting-started/command_data_implementations.png" alt="&lt;code&gt;Command Data&lt;/code&gt; implementations"></p>
<h4 id="Verify"><a href="#Verify" class="headerlink" title="Verify"></a>Verify</h4><p>As this is what contracts are supposed to do, it implements a <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L35"><code>verify(tx)</code></a> function. If the contract wants to reject a transaction, all it has to do is throw an exception. If it does not throw an exception, then it accepts the transaction.</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">verify</span><span class="params">(LedgerTransaction tx)</span> </span>&#123;</span><br><span class="line">    <span class="keyword">final</span> CommandWithParties&lt;Commands.Create&gt; command = requireSingleCommand(tx.getCommands(), Commands.Create.class);</span><br><span class="line">    requireThat(require -&gt; &#123;</span><br><span class="line">        <span class="comment">// Generic constraints around the IOU transaction.</span></span><br><span class="line">        require.using(<span class="string">&quot;No inputs should be consumed when issuing an IOU.&quot;</span>,</span><br><span class="line">                tx.getInputs().isEmpty());</span><br><span class="line">        require.using(<span class="string">&quot;Only one output state should be created.&quot;</span>,</span><br><span class="line">                tx.getOutputs().size() == <span class="number">1</span>);</span><br><span class="line">        <span class="keyword">final</span> IOUState out = tx.outputsOfType(IOUState.class).get(<span class="number">0</span>);</span><br><span class="line">        require.using(<span class="string">&quot;The lender and the borrower cannot be the same entity.&quot;</span>,</span><br><span class="line">                !out.getLender().equals(out.getBorrower()));</span><br><span class="line">        require.using(<span class="string">&quot;All of the participants must be signers.&quot;</span>,</span><br><span class="line">                command.getSigners().containsAll(out.getParticipants().stream().map(AbstractParty::getOwningKey).collect(Collectors.toList())));</span><br><span class="line"></span><br><span class="line">        <span class="comment">// IOU-specific constraints.</span></span><br><span class="line">        require.using(<span class="string">&quot;The IOU&#x27;s value must be non-negative.&quot;</span>,</span><br><span class="line">                out.getValue() &gt; <span class="number">0</span>);</span><br><span class="line"></span><br><span class="line">        <span class="keyword">return</span> <span class="keyword">null</span>;</span><br><span class="line">    &#125;);</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>Let’s explore some constructs before coming back to the code above with explanations.</p>
<h5 id="requireSingleCommand"><a href="#requireSingleCommand" class="headerlink" title="requireSingleCommand"></a><code>requireSingleCommand</code></h5><p>As the name suggests, it extracts a single command from the transaction. Of note is that:</p>
<ul>
<li>It expects to be given the type of command to find, here <code>Commands.Create.class</code>. Passing a less precise <code>Commands.class</code> would work too.</li>
<li>It throws if <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/ContractsDSL.kt#L80-L81">none can be found</a>, expressed in the <code>require</code> wording of the function.</li>
<li>It throws if <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/ContractsDSL.kt#L79">more than one is found</a>, expressed in the <code>single</code> wording.</li>
</ul>
<p><code>requireSingleCommand</code> is in fact part of a wider set of utilities, the Contracts DSL.</p>
<h5 id="ContractsDSL"><a href="#ContractsDSL" class="headerlink" title="ContractsDSL"></a><code>ContractsDSL</code></h5><p>Notice <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/contracts/ContractsDSL.kt#L30"><code>requireThat</code></a>, which is not a Java or Kotlin word but instead part of a Domain-Specific Language (a.k.a. DSL) created by Corda to increase the expressiveness of your code, if not the mechanisms enabling it… <code>requireThat</code>, when used <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-kotlin/src/main/kotlin/com/example/contract/IOUContract.kt#L34-L36">in Kotlin</a>, is more succinct than when used <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L37-L40">in Java</a>.</p>
<p> Optional rabbit hole about <code>requireThat</code></p>
<p>Why go through all this trouble when the Java syntax is not necessarily the most expressive? It removes the visual noise of the usual pattern, e.g. <code>if (!happy) &#123; throw new IllegalArgumentException(&quot;why not&quot;); &#125;</code> and it lets you focus on the important elements of the constraints: <code>happy</code> and <code>&quot;why not&quot;</code>. The Corda team themselves are big users of Kotlin, so they benefited from their own efforts.</p>
<h5 id="Other-points"><a href="#Other-points" class="headerlink" title="Other points"></a>Other points</h5><p>Do not miss the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L13">Java static imports</a>. IntelliJ may fold the code near line 3. Expand the fold to reveal important dependencies.</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> <span class="keyword">static</span> net.corda.core.contracts.ContractsDSL.requireThat;</span><br></pre></td></tr></table></figure>

<p>A couple of notes about the requirements in the <code>verify</code> function:</p>
<ul>
<li><p>It was mentioned earlier that the <code>IOUState</code> did not itself ensure that the <code>value</code> is strictly positive. You now see that <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L50-L51">it is enforced here</a>, in the <code>verify</code> function, among all other constraints.</p>
</li>
<li><p>It is very restrictive in that it requires:</p>
<ul>
<li><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L36">a single IOU Create command</a>,</li>
<li>absolutely <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L39-L40">no inputs</a></li>
<li>and <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L41-L42">a single output</a> which must be of IOU type.</li>
</ul>
<p>Note that the contract still allows a transaction where another non-IOU Create command is present. This is welcome. It means you could hypothetically mix this contract with a Token state and contract. The Token would be the owed value of the “I owe you” idea. Indeed, you may want to create the IOU state at the same time you transfer some tokens in an atomic way. To make this possible, the restriction on inputs and outputs would have to be adjusted so that the IOU contract only checks the <code>IOUState</code>s. In effect:</p>
<p>JavaKotlin</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">require.using(<span class="string">&quot;No IOU inputs should be consumed when issuing an IOU.&quot;</span>,</span><br><span class="line">    tx.inputsOfType(IOUState.class).isEmpty());</span><br><span class="line"><span class="comment">// Notice inputsOfType, which allows you to only select the type you care about.</span></span><br><span class="line">require.using(<span class="string">&quot;Only one output state should be created.&quot;</span>,</span><br><span class="line">    tx.outputsOfType(IOUState.class).size() == <span class="number">1</span>);</span><br><span class="line"><span class="comment">// Notice outputsOfType, which allows you to only select the type you care about.</span></span><br></pre></td></tr></table></figure>

<p>Doing so would signal that this contract only cares about its states, in effect delegating the control of the Token states to the Token contract.</p>
</li>
<li><p>Both the Java and Kotlin versions make assumptions on outputs size and then getting the first, or only, state. However they awkwardly make those assumptions on different lists. The size is checked on the absolute list of outputs <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L41-L42">here</a> and <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-kotlin/src/main/kotlin/com/example/contract/IOUContract.kt#L37">there</a>. This absolute list of outputs contains <code>IOUState</code>s and states of other types. So when the first element is taken in Java on the <em>modified</em> list of <code>IOUState</code>, this modified list may well be empty, and the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L43"><code>.get(0)</code></a> yield an <code>IndexOutOfBoundsException</code>. Similarly in Kotlin, the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-kotlin/src/main/kotlin/com/example/contract/IOUContract.kt#L38">only element</a> is taken on the modified list, which may well be empty. An improvement to both contracts would be to make sure the size is checked on the modified <code>tx.outputsOfType&lt;IOUState&gt;()</code> list as seen on the samples above. This improvement would yield more intelligible error messages on invalid transactions.</p>
</li>
<li><p>Notice how the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L36">command</a> is picked at the beginning of the <code>verify</code> function. If the command is missing or there is more than one of this type, it will fail. Notice too how the require was on <code>Commands.Create.class</code>, this means that if you want to add other commands to your contract, in order to signal other intents, then you will need to revisit this line and use the parent class <code>Commands.class</code> instead. This should become clearer when you code, in the next module.</p>
</li>
<li><p>Finally, it requires that the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/contract/IOUContract.java#L46-L47">participants need to <del>have signed off</del> be marked as signers</a> on the transaction. Correct, the contract does not check the signatures. Instead the transaction, via the commands, here <code>Create</code>, informs which signers are required and the contract checks that the expected signers are listed, and then only the Corda system makes sure that the signatures of the required signers are present before accepting a transaction as final. Belaboring the point, the contract verifies who needs to have signed off, it does <em>not</em> verify the signatures. Verifying the signatures, and verifying that all the required signers have indeed signed is the purview of the Corda framework, before it commits the new transaction to the node’s ledger. What was the rationale behind asking both participants to sign?</p>
<ul>
<li>asking the borrower is absolutely necessary. After all, this IOU is a liability for the borrower, so you need to confirm that the borrower is ok with acquiring a new liability. Otherwise it would be too easy to just drop IOUs on rich people. <em>IOU printer go brrrr</em></li>
<li>asking the lender is less clear-cut. After all, the lender gains an asset, the future value that the borrower is promising to return. Who would reject helicopter money? On the other hand, entering an IOU may be legally binding, or may have tax implications, which both represent a liability for the lender. Since that is the case, the lender signature should be required. Additionally, as this is an example CorDapp, there was a desire to demonstrate a flow that requires signing from a counterparty.</li>
</ul>
</li>
</ul>
<p>In effect, the contract is in charge of validating transitions of the state machine. Valid transitions are expressed in the following diagram:</p>
<p><img src="https://training.corda.net/getting-started/cdl_iou_state_machine.png" alt="IOU State Machine View"></p>
<p>Where SC is short for <em>Signing Constraints</em>.</p>
<p>Finally the <code>Contract</code> interface, it too has some available implementations:</p>
<p><img src="https://training.corda.net/getting-started/contract_state_implementations.png" alt="&lt;code&gt;Contract&lt;/code&gt; implementations"></p>
<h3 id="Flow"><a href="#Flow" class="headerlink" title="Flow"></a>Flow</h3><p>You have learned that flows encapsulate a piece of the business process. They can be used to create valid transactions agreed between parties. Note the wording in the previous sentence: <em>can be used</em>. Indeed, although a flow encapsulates a piece of the business process, creating a signed transaction is only one of the business processes an organisation implements. Admittedly an important one.</p>
<p>In the process of our example, there are 2 parties, the lender and the borrower, and they both need to sign off, a.k.a. agree, on the transaction proposal. They want to arrive at a consensus and achieve this state evolution:</p>
<p><img src="https://training.corda.net/getting-started/cdl_iou_state_evolution.png" alt="IOU State Evolution View"></p>
<p>Note the difference from the previous state machine view, seen before. Here, a single state evolution is expressed, one that reaches a state with well-defined values.</p>
<p>To achieve this consensus, the flow goes through a number of steps:</p>
<p><img src="https://training.corda.net/getting-started/cdl_create_iou_bpmn.png" alt="Create IOU BPMN"></p>
<p>As you will see later, it was a design decision to have the lender initiate the process and for the borrower to then accept the transaction proposal. The back and forth business process is expressed in:</p>
<ul>
<li>The <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L33-L35"><code>Initiator extends FlowLogic&lt;&gt;</code></a>, which, you will notice is annotated with <code>@InitiatingFlow</code>.</li>
<li>The <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L122-L123"><code>Acceptor extends FlowLogic &lt;&gt;</code></a>, which is annotated with <code>@InitiatedBy(Initiator.class)</code>.</li>
</ul>
<p>In other flow examples you will often see this <em>initiator</em> / <em>responder</em> naming convention.</p>
<h4 id="About-the-Flows"><a href="#About-the-Flows" class="headerlink" title="About the Flows"></a>About the Flows</h4><p>Both classes could be in their own file, and it was again a design decision to encapsulate both as <code>static</code> classes inside a class for Java, or in a singleton <code>object</code> for Kotlin. Also, it is not immediately apparent that it is the lender that needs to initiate the process, this detail reveals itself in the code.</p>
<p>Flows are <strong>asynchronous</strong> processes. However, they are written as synchronous code. With the help of <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/build.gradle#L4">Quasar</a>, a flow’s context and execution step can be <em>frozen</em> and saved to disk, a.k.a. checkpointed; and they can be <em>revived</em> later when necessary. This mechanism dispenses with constructs like callbacks or <code>await</code> that should be familiar to you. To indicate to Quasar that a given function’s body can be checkpointed mid-flight, the function’s declaration needs to be annotated with <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L80"><code>@Suspendable</code></a>. And you see that both <code>Initiator</code> and <code>Acceptor</code> have this <code>call()</code> function that is suspendable.</p>
<p>A typical reason for flow suspension is when it expects to receive something. At this point, it is suspended, and will be resumed when there is something to receive indeed.</p>
<p>Since a flow can be suspended, there is a mechanism that lets observers know at what stage the flow is. That is the role of the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L72-L75"><code>progressTracker</code></a>. <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L109">Before</a> and <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L116">after</a> checkpoints, or <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L87">any</a> <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L99">other</a> <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L104">point</a> really, it can be updated with a descriptive state.</p>
<p>When a flow is suspended, it frees the <em>thread</em> on which it was running. This available thread can be used by a brand new flow, or a suspended one whose <em>revival conditions</em>, have been met such that it can now continue. If not, the thread remains unused until such case arises. This should remind you again of co-routines, which <del>pop in and out of threads</del> are suspended and resumed on the same or another thread.</p>
<p>From the outside, it therefore looks like flows are running concurrently, with all the opportunities for race conditions and deadlocks this entails. You, the developer, have to be mindful of this when you establish process dependencies between flows, in particular with regards to the vault’s database.</p>
<p>The <code>Initiator</code> is annotated with <code>@InitiatingFlow</code> and the<code>Acceptor</code> is annotated with <code>@InitiatedBy(Initiator.class)</code>. This means that once the <code>Initiator</code> flow has made its first contact with a peer node, the <code>Acceptor</code> flow is automatically instantiated on the peer node:</p>
<ul>
<li>At this point, the 2 flow instances are connected to each other by a <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L127"><code>FlowSession</code></a>, akin to a <em>session id</em> identifying the 1-to-1 link.</li>
<li>If the initiator makes contact with more than 1 peer node, then there are as many 1-to-1 sessions as there are peer nodes, with 1 responder flow instance per peer node.</li>
<li>Additionally, if the <code>Initiator</code> ever needs to ask more than one piece of information from the <code>Acceptor</code> flow, it can keep asking for those pieces on the same session. The <code>Acceptor</code> flow would, of course, need to be coded so that it also receives and sends the information in accordance with the <strong>choreography</strong> coded in the <code>Initiator</code>.</li>
<li>Even while 2 peer nodes are linked by a session between 1 instance of an initiator flow and 1 instance of a responder flow, nothing prevents the same 2 peer nodes from creating a new session between 2 flow instances of the same type or of different types.</li>
</ul>
<p>For the avoidance of doubt, know that <strong>not</strong> all flows come in pairs. Indeed, you may create a so called unary flow to make a calculation, query and return local data or query an external API. Additionally, even if flows come in pairs, there are 2 types of pairs:</p>
<ul>
<li><strong>Auto-initiated session pair</strong>, as seen above, whereby the flows have been annotated with <code>@InitiatingFlow</code> and <code>@InitiatedBy(XX.class)</code>.</li>
<li><strong>Inlined</strong> or <strong>free-riding pair</strong>, whereby the <em>responder</em> is not automatically awoken by the <em>initiator</em>, but instead it is the responsibility of the encapsulating flows to both launch the initiator and the responder at the right point in the choreography, as you’ll see with <code>CollectSignaturesFlow</code>. Inlined flows always take at least one flow session among their constructor parameters.</li>
</ul>
<p>A productive way to look at flows is as small pieces of a workflow that can be composed or chained together in order to achieve a larger orchestration.</p>
<p>Another point is that, in this example, the <code>Initiator</code> and the <code>Acceptor</code> flows have been coded together by the same developer, and distributed to interested parties. In real life, each party would subclass these flows in order to add custom, and private, code for their internal processes, while sticking to the agreed common <strong>choreography</strong> defined by the base class.</p>
<h4 id="ExampleFlow-Initiator-flow"><a href="#ExampleFlow-Initiator-flow" class="headerlink" title="ExampleFlow.Initiator flow"></a><code>ExampleFlow.Initiator</code> flow</h4><p>Here, the initiator flow creates the full transaction proposal and then only sends it for acceptance. So the flow:</p>
<ul>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L84">Gathers the notary</a>.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L90">Creates the <code>IOUState</code></a>. Notice that <code>me = getOurIdentity()</code> is placed in the <code>lender</code> position. So really this flow has to be started by the lender. The code could make this a bit more explicit, for instance, when using Kotlin’s <a target="_blank" rel="noopener" href="https://kotlinlang.org/docs/reference/functions.html#named-arguments">named arguments</a>, like so:</p>
<p>Copy</p>
<figure class="highlight kotlin"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">val</span> iouState = IOUState(</span><br><span class="line">    value = iouValue,</span><br><span class="line">    lender = serviceHub.myInfo.legalIdentities.first(),</span><br><span class="line">    borrower = otherParty)</span><br></pre></td></tr></table></figure></li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L91-L93">Creates a command</a> with the required signers.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L95">Associates</a> the <code>IOUState</code> with the <code>IOUContract</code>. This is where the state is actually <em>pointing</em> to the contract that will verify the transaction on its behalf. In fact, the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/contracts-java/src/main/java/com/example/state/IOUState.java#L22"><code>BelongsToContract</code></a> annotation allows the compiler to add cross-checks in order to minimize mistakes. There is the <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/contracts/Structures.kt#L342"><code>StateAndContract</code></a> class that you could use too in order <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/transactions/TransactionBuilder.kt#L120">to achieve the same</a>.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L101">Verifies locally</a> that the transaction is valid. Do you remember that the contract does not check for the presence of signatures, only of expected signers? Here the contract accepts the transaction before it has been signed.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L106">Signs it</a> with the lender’s signature.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L111">Opens a peer-to-peer session</a> with the borrower, <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/flows/FlowLogic.kt#L144-L149">without sending</a> anything yet. The remote peer will be notified only when an actual request is made.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L112-L113">Asks for signatures</a> from the borrower. This triggers a checkpoint on the initiating peer as the initiating peer awaits a fully signed transaction.</p>
</li>
<li><p>At some point it receives the fully signed transaction and carries on.</p>
</li>
<li><p><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L118">Finalizes</a>, without communicating with the notary in this case because there are no input states, by sending the transaction to the borrower. You could choose to send it to more than the <code>participants</code>, for instance to a regulator or observer.</p>
</li>
</ul>
<p>There are quite a number of steps although they should make sense. Notice how, when asking for signatures, it specifically calls <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/flows/CollectSignaturesFlow.kt#L67"><code>CollectSignaturesFlow</code></a>, which is an inlined flow, not a <code>@InitiatingFlow</code>. This means that the <code>Acceptor</code> flow will have to respond with the responder <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/flows/CollectSignaturesFlow.kt#L261"><code>SignTransactionFlow</code></a> at the appropriate position in the choreographed sequence.</p>
<p>Notice how <code>CollectSignaturesFlow</code> asks you to pass <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/flows/CollectSignaturesFlow.kt#L68"><code>val sessionsToCollectFrom: Collection</code></a> the list of sessions to use. Why is that? Can’t it not deduce it on itself? You see, <code>CollectSignaturesFlow</code> is not <code>@Initiating</code>. When you are in an <code>@Initiating</code> flow, and you do <code>initiateFlow(bob)</code> the first time, you always have the assurance that you just created a new session. That is not the case for inlined flows, like here, which are called from another flow. In this situation, a session may already have been created, so, calling <code>initiateFlow(bob)</code> will fail. Therefore these flows have to piggy-back on existing sessions, and that is why, if your inlined flow has a responder, it has to take the pre-existing sessions in its constructor.</p>
<h4 id="ExampleFlow-Acceptor-flow"><a href="#ExampleFlow-Acceptor-flow" class="headerlink" title="ExampleFlow.Acceptor flow"></a><code>ExampleFlow.Acceptor</code> flow</h4><p>As mentioned earlier, this flow is annotated with <code>@InitiatedBy</code> so that it is bound to and responds to <code>Initiator</code> flows, and its sub classes. If you recall, the initiator initiates 2 actions that involve the responder:</p>
<ol>
<li>It calls <code>CollectSignaturesFlow</code>.</li>
<li>And <code>FinalityFlow</code>.</li>
</ol>
<p>Neither “sub” flow is annotated with any <code>@InitiatedBy</code>, so the responder, as part of its run, <strong>has to</strong> launch their respective responder actions, which, <strong>in order</strong>, are none other than:</p>
<ol>
<li><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L151">Calling <code>SignTransactionFlow</code></a>, which conditionally adds a signature to the transaction,</li>
<li><a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/cf21fb3dbf9972d61eb9b543e6fe79698f843110/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L153">and <code>ReceiveFinalityFlow</code></a>, which conditionally saves the transaction to the vault.</li>
</ol>
<p>Fear not, there is no guess-work involved here. If you go to:</p>
<ul>
<li><code>CollectSignaturesFlow</code>, you will find the responder <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/flows/CollectSignaturesFlow.kt#L261">on the same page</a>. The JavaDoc even <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/flows/CollectSignaturesFlow.kt#L25-L26">mentions it</a>.</li>
<li><code>FinalityFlow</code>, the responder is <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/68bb7a0e7bb900117c2ed0d9174fea36d3d4aedc/core/src/main/kotlin/net/corda/core/flows/FinalityFlow.kt#L272">documented there</a> too.</li>
</ul>
<p>As you may have suspected, it is always a good decision to keep the flow pair in a single file.</p>
<h2 id="look-into-DB"><a href="#look-into-DB" class="headerlink" title="look into DB"></a>look into DB</h2><p>then, inside <code>workflow-java/build.gradle</code>’s <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/cordapp-example/workflows-java/build.gradle#L71-L73"><code>deployNodes.nodeDefaults</code></a>, set the H2 database port by adding the below section:</p>
<p>Copy</p>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">nodeDefaults &#123;</span><br><span class="line">        projectCordapp &#123;</span><br><span class="line">            deploy = <span class="literal">false</span></span><br><span class="line">        &#125;</span><br><span class="line">        cordapp project(<span class="string">&#x27;:contracts&#x27;</span>)</span><br><span class="line">        cordapp project(<span class="string">&#x27;:workflows&#x27;</span>)</span><br><span class="line">        runSchemaMigration = <span class="literal">true</span> <span class="comment">//This configuration is for any CorDapps with custom schema, We will leave this as true to avoid</span></span><br><span class="line">        <span class="comment">//problems for developers who are not familiar with Corda. If you are not using custom schemas, you can change</span></span><br><span class="line">        <span class="comment">//it to false for quicker project compiling time.</span></span><br><span class="line">        extraConfig = [</span><br><span class="line">                <span class="symbol">h2Settings:</span> [</span><br><span class="line">                        <span class="comment">// A random port will be selected.</span></span><br><span class="line">                        <span class="attr">address :</span> <span class="string">&#x27;localhost:0&#x27;</span></span><br><span class="line">                ]</span><br><span class="line">        ]</span><br><span class="line">    &#125;</span><br></pre></td></tr></table></figure>

<p>Then:</p>
<ol>
<li><p>Build the nodes as you did earlier.</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">gradle deployNodes --build-file .\build.gradle</span><br></pre></td></tr></table></figure></li>
<li><p>Run the nodes as you did earlier.</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">F:\space_hsdc\samples-java\Basic\cordapp-example&gt; .\build\nodes\runnodes</span><br></pre></td></tr></table></figure></li>
<li><p>On each running node shells, you should see a new line, like:</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"># Party B</span><br><span class="line">Database connection url is              : jdbc:h2:tcp:&#x2F;&#x2F;localhost:51004&#x2F;node</span><br><span class="line"></span><br><span class="line"># Notary</span><br><span class="line">Database connection url is              : jdbc:h2:tcp:&#x2F;&#x2F;localhost:51007&#x2F;node</span><br><span class="line"></span><br><span class="line"># Party A</span><br><span class="line">Database connection url is              : jdbc:h2:tcp:&#x2F;&#x2F;localhost:51009&#x2F;node</span><br></pre></td></tr></table></figure></li>
</ol>
<p>F:\space_hsdc\samples-java\Basic\cordapp-example\build\nodes.cache\apps\net.corda.node.Corda_4.9\h2-1.4.199.jar</p>
<ol start="4">
<li>双击这个jar，然后填jdbc url到h2 console.</li>
</ol>
<p><img src="C:\Users\51606\AppData\Roaming\Typora\typora-user-images\image-20221218221138953.png" alt="image-20221218221138953"></p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"># this sql only can run in notary</span><br><span class="line">SELECT * FROM NODE_NOTARY_REQUEST_LOG</span><br></pre></td></tr></table></figure>

<p>Press Run. There are no rows. This means that as of now you have not had any state that was consumed.</p>
<p>connect to PartyA. Click on <code>VAULT_STATES</code> and Run. Again, empty.</p>
<h3 id="Create-your-second-IOU"><a href="#Create-your-second-IOU" class="headerlink" title="Create your second IOU"></a>Create your second IOU</h3><p>Well, it will be the first as far as these newly reconfigured nodes are concerned. Just like before, run this in the shell on the PartyA node:</p>
<p>Copy</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">Sun Dec 18 22:22:25 CST 2022&gt;&gt;&gt; flow start ExampleFlow<span class="variable">$Initiator</span> iouValue: 50, otherParty: <span class="string">&quot;O=PartyB,L=New York,C=US&quot;</span></span><br><span class="line">Starting</span><br><span class="line">Generating transaction based on new IOU.</span><br><span class="line">Verifying contract constraints.</span><br><span class="line">Signing transaction with our private key.</span><br><span class="line">Gathering the counterparty<span class="string">&#x27;s signature.</span></span><br><span class="line"><span class="string">Collecting signatures from counterparties.</span></span><br><span class="line"><span class="string">Verifying collected signatures.</span></span><br><span class="line"><span class="string">Obtaining notary signature and recording transaction.</span></span><br><span class="line"><span class="string">Broadcasting transaction to participants</span></span><br><span class="line"><span class="string">Done</span></span><br><span class="line"><span class="string">Flow completed with result: SignedTransaction(id=45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2)</span></span><br><span class="line"><span class="string"></span></span><br><span class="line"><span class="string">Sun Dec 18 22:22:35 CST 2022&gt;&gt;&gt;</span></span><br></pre></td></tr></table></figure>



<h4 id="PartyA’s-H2-browser-tab"><a href="#PartyA’s-H2-browser-tab" class="headerlink" title="PartyA’s H2 browser tab"></a>PartyA’s H2 browser tab</h4><p>Rerun the <code>VAULT_STATES</code> query. Now you have 1 state. The IOU you just created. Notice how the state mentions:</p>
<p>1.SELECT * FROM VAULT_STATES;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">OUTPUT_INDEX </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">TRANSACTION_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONSUMED_TIMESTAMP </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONTRACT_STATE_CLASS_NAME </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">LOCK_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">LOCK_TIMESTAMP </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">NOTARY_NAME </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">RECORDED_TIMESTAMP </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">STATE_STATUS </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">RELEVANCY_STATUS </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONSTRAINT_TYPE </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONSTRAINT_DATA </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">0</td>
<td align="left">45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2</td>
<td align="left"><em>null</em></td>
<td align="left">net.corda.samples.example.states.IOUState</td>
<td align="left"><em>null</em></td>
<td align="left"><em>null</em></td>
<td align="left">O=Notary, L=London, C=GB</td>
<td align="left">2022-12-18 14:22:35.685</td>
<td align="left">0</td>
<td align="left">0</td>
<td align="left">3</td>
<td align="left">3059301306072a8648ce3d020106082a8648ce3d03010703420004038d226dcd0fa574316da478aa75225e6ce18f65cbd96e60bf3c8251b196541756e5dcf7ccab21b712601ed0278501f2f33d0b5fdaa4c09e62639464e4910871</td>
</tr>
</tbody></table>
<p>(1 row, 7 ms)</p>
<ul>
<li>The transaction id of the transaction that created it.</li>
<li>The <code>output_index</code> of <code>0</code>, it was the only output after all.</li>
<li>The contract class name that it is associated with.</li>
<li>The notary name that will record its eventual consumption.</li>
<li>The interestingly named <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/node/src/main/kotlin/net/corda/node/services/vault/VaultSchema.kt#L61-L62">state_status</a>, which is now <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/node/services/VaultService.kt#L124-L126">unconsumed</a>.</li>
</ul>
<p>Now, run the same <code>*</code> query on another table: <code>SELECT * FROM IOU_STATES</code>. Here again, you have a single state:</p>
<p>2.SELECT * FROM IOU_STATES;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">OUTPUT_INDEX </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">TRANSACTION_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">VALUE </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">LENDER </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">BORROWER </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">LINEAR_ID </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">0</td>
<td align="left">45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2</td>
<td align="left">50</td>
<td align="left">O=PartyA, L=London, C=GB</td>
<td align="left">O=PartyB, L=New York, C=US</td>
<td align="left">d68e6752-f1a8-4f7c-8b25-e875a2a18cab</td>
</tr>
</tbody></table>
<p>(1 row, 5 ms)</p>
<p>You will recall that a state is uniquely identified by the transaction that created it, and its index in the list of created outputs. This pair of identifiers is neatly packaged in the <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/contracts/Structures.kt#L154-L163"><code>StateRef</code></a> class. Therefore, you should expect to see this pair in different places:</p>
<ul>
<li>In both <code>IOU_STATES</code> and <code>VAULT_STATES</code>, their primary key is the pair <code>(OUTPUT_INDEX, TRANSACTION_ID)</code>. Both values were persisted thanks to the <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/cordapp-example/contracts-java/src/main/java/com/example/schema/IOUSchemaV1.java#L22">parent schema of <code>PersistentIOU</code></a>, i.e. the schema of <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/schemas/PersistentTypes.kt#L85"><code>PersistentState</code></a>:</li>
</ul>
<ol start="3">
<li><p>SELECT * FROM NODE_ATTACHMENTS</p>
<p>SELECT * FROM NODE_ATTACHMENTS;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">ATT_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONTENT </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">FILENAME </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">INSERTION_DATE </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">UPLOADER </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">VERSION </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">D120F4F7FF3EAEF9D6937E7B6DA8774F1F3F258E44D25AE2EED04D343E61E519</td>
<td align="left">504b0304140008080800518e9255000000000000000000000000140000004d4554412d494e462f4d414e49464553542e4d469d924b93a2301485f756f91f58b8ebf1018aa855b340c417c447033aed2e13226043401204f9f5838c4e4d4d4b9535bbe4dee47ee79c0440e21d3165cd1d8ea9179211c7b73af59a12c6368ca2a612121643746b133b8c475cd9e0d611269c112631c24fcf3e463d69ae6080ef638a32ce6010f9987bb469bd66c2d8c1acb9f1213b8671f0d7b4429781a18fed11c7e2a420038f549cfb82d53d84092ac87204918bb9724ff137ee7e8d136eb6ebb5dff208666d741bd1a6a53edabe0b2daa77a1edc5da7a4c6f2861104062d3861263c870ab5ee3900f69e1c698cb4d41ec37279e53a45ce013a08f8d4d9cbf596b7386fcd0a64c93f27d7e1c9201a0538b4d3e4430ee6baefcfd153db43013c09b18a35cb52ab899c95ff229c00ec148daeb0bab3b063dd7ea62fe2cabbd0f134cc4e3fa9dda02765ee23ecda10aaeacedebf51c9c8d4bda25938549accd6019f495311e5c14d7414a8466b42d6e7fecadd74cb322e4926cdc5655d82ee5b5a9e5f1ab04cfd04e1693d340c8a7e3e4301bce9de55ce20fa9ca3a52443ec1ff7bfef3f6552aa0f3360eb7ced066e250c975e65e7e0666473788646e2df50467d7795719a044e35f4bfedf17dff18dcded0f5386092baa553a96e82820329cebebcce0579aca0c6bf929efa16af402557f9f7ab3d4f706d2c407afa5f1554715d985aa0efd30c2ae6f8ac27997e6e141536c4139810c647b92f9f2213d5f90b04a4bf22f504b0708bd0395cb1102000094040000504b0304140008080800518e9255000000000000000000000000140000004d4554412d494e462f434f524441434f442e53469d934b8fa2401485f726fe0716bd98c94401697c25bd00a4155a908788ba9914580222afaa42c05fdf68cf6a324e4cef4e5552f73be7dc941d0529202582bd0d4438cad229c5f6996ec75e08bd013feccda20062d2d3401a1dbf4494f6044250e49504e229b5f7dcb5cbeb33ce0a56897b96e68916885e2c64abd72aec76a809d9791973590d4f8a35f4df1e4e9e52e6a9121d7179b43cae761a88e6285ef8717306ca5582e5561716e949c17880664e3b4642101078e889cdcdf1b8cffc1e3003eac70a01ff0c2929437986006903fdec76ba1d1d24704aa590d07e860e80c620c9cf10d3b0be8bf63625ed4b826965e5487f0e2f529624203de0972f58bf8de39f01c67f879852dce60c9623bee627ecba80fa9a7b0d169a481ff8f8ddd9f886571dc5340b346ed9c46fcff8c17e0813703363df55ff01f7185c837c3198c9a3a4d9892edbd0c54944c92561699d07a193e32af06d6d9c8fe4a7b8ffece111dcbf0a4de88cb9895be65b46d78ccb60cfeb0619c2081cebdc2a4a79de54bb500bb3e74293b6e43bd9bea947d8ea62176298da5a594b2a54874a1a1786c420fb42daaeac601b6949e6be2ba7e1735dff7ff78f5c28f89d395b8b5f487d9d84f27a0f640db1b93c5e970e77f0b8c97ea78388b1eaab39fed6c637ec8b71fb9198c094b4b78f7ce4b5e414fe873a568d66e45750358b09bfdc9ae969550aa60b047eb9a177d7b5c97ed7c7237269541f6a3e33a4c295dba10dd2234165b6680e16ca2ed483cd109433353ed49579277f02504b0708f597f2e3300200006b040000504b0304140008080800518e9255000000000000000000000000140000004d4554412d494e462f434f524441434f442e4543336862facfc6a9d5e6d1f69d97919d694113d3078326a6374c8c8c86fc06bc6c9c096d1e8ca9cc2c4c8cac0c06dc08858c0b9a183f1b3431be07e2c90b989918999858c455abcb0d78d838806aced9b230330175441b721b70b23187b2b00933b93b814d0472d879d87cf2f352f2f30cf980ea81025c3caccef945298930d5dc3c4c41c686720632200e338f285852c125b54cc1393f25552138333d2fb5c8404e9cd7c8c0c0ccc8d4d0c2d4c8d4244a9cd718c435867271592e8c6eb9309ae5c2c8960be3b03cd240988d1dec532646a8979919d9999d1858987b9572cff22f2d31cc5d52b1aa54292ee7617feae99b7909fb6d9a02374e0b110f7b7ae7fb99d58adb8512e42ea8b7327efa6ccb1d7f6bc9817949c953529e4ce4285cec6ce008349c3954569585c7808b8d439b8d9195959d991918fe40417e1660d0b23718c882387c2c622c229b55f4339f260abd6f9c96f5268963e5f61da5ff3451e381d983c1c0954991614349d79c2aa199c157bf5dd15a21f36ec7f15f534b5df93434e2274ffc71be5cf200938236eb058eebb33bdefbc8ff96f43eeb3fb1784ecfd6c3331eff5c91eab5fdd55e8e69868d170d1acf01538741324d23179a9a3012202cc85919583c0cdc805efad9775bffc884e5a59cbe6dcf6fe7bffcc8142fcaa5946cd1ba4ef885e0b1c745df814a4ece8ce8e6fdeafd5f6ab3e3f68bd6d2ae7bfee74ff8ce9b96b27cffcaaddb048a4e0000504b070844c58c211302000003030000504b030414000808080000004100000000000000000000000000090000004d4554412d494e462f0300504b0708000000000200000000000000504b030414000808080000004100000000000000000000000000040000006e65742f0300504b0708000000000200000000000000504b0304140008080800000041000000000000000000000000000a0000006e65742f636f7264612f0300504b0708000000000200000000000000504b030414000808080000004100000000000000000000000000120000006e65742f636f7264612f73616d706c65732f0300504b0708000000000200000000000000504b0304140008080800000041000000000000000000000000001a0000006e65742f636f7264612f73616d706c65732f6578616d706c652f0300504b0708000000000200000000000000504b030414000808080000004100000000000000000000000000240000006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f0300504b0708000000000200000000000000504b030414000808080000004100000000000000000000000000450000006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e747261637424436f6d6d616e6473244372656174652e636c617373a5514d4bc340149c6dd3a489d1d6f875167a500feec583e01712100ac11ed4de37c9a229c946365bf16f79123cf803fc51e2cbb6825795856166f6bd79ecbe8fcfb7770047d809d0c5ba87c8c386872d06f7b450853967e8eeed4f199cb8ce25c3202994bc9e57a9d4b7222dc989923a13e554e8a2d54bd3310f45c3d08febaa122a271a8e95923a2e45d348926eaca53054799928697856eb5cf046548fa56cb87cb6845c65b4c84cc3c793bb782946df99a345c409437053cf7526af8a76f4f047ede14c3c89103db80c17ff9c43c96d1a2f85bae793742633e3619be1f8afb90cfc97add84587b644df4b2b6374e861841e296e35d03b78057b21d2419fd0b5e6197cc2705180006bf67e6071483e101173b08915d7b76c15fe17504b0708fb7b2bc11c0100001a020000504b0304140008080800000041000000000000000000000000003e0000006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e747261637424436f6d6d616e64732e636c6173739d4f3b6ec240107d038917f3091667709d6d52a44be128922b17280718ec11c2b2d7d1ee26e26c141c2087422c2611b430d2bcf9bfa7f93decf6005e90284c14a60a33c228ebda964de508d3dc18b159c3ce89537822449915f642182fbb6f5bcac7a6094592179f5967bce5d23fd7fcc30a73c2ab11afcbce56ac1db75f8d382ddb3e09ddf3b2d35797e945383991e886cd5a17ab5a4a4f482f6c01af29feceded933e1ed5ed1f4ff337d234344200c820f71b201463dc6780c71d14fc6788862442153888f504b07082b457a09c600000075010000504b030414000808080000004100000000000000000000000000350000006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e74726163742e636c617373b557fb7f1c5515ffdedd7427dd4c93ed428ba502539a924d9aecb60804dddad2a654229ba692926a157576f72699667666d9994d9b2a283e0a3e51045154ac4f7c0b3ed2a62ae25bd1bfc9fabd7736c9a69bc42e7efc61eee3dc73ce3d8fef3df7ceebffbef22a80bbf0cf2476e3c1240a1833703c89719c487361528d4e75e2dd6ae53d5d388df726f13e3cd289f72bca0714e583066c3529aa49a913e524ba21553395c434663ae1247106b38ae22a9e4a1a02d52e3c8a5a12014235aa1b98536b673b714e31ce27711e1f32f061038f1978dcc047043a47fc4ac5f6ca818039ea79b236e2da4120398d8d1e154817ced87376ceb5bde9dc445873bce9bcc09611df0b42db0b276db72e3bf15181c401c773c28302f14cffa440c7885f96023d05c793c7eb95a2ac9db48bae54fafc92ed4eda3547cd1bc48e70c6e186fb0b9e0c7325bf56b673815da9ba32c8c9737a40aa17d6ec5218e446c71f1e694c684a624ed69ca979813b334dd26c658e2c5e402e87c6e60ab23c4d2356487965662c3c27906b5350c02845311318ba5676c5ce465c4f39e1cc09bb163a32a0e4f6d5eecf5797429018a9493be4a0da8ec603ed46ac7729dbbdd17ef983342a3526c319bf4c9d764586b2c654f4b876a558b67ba3e8f6ee1378beddf8b61599f5991f928fd69d9aac482f0cf2fd4d681c2f9e911a02462d6211e8bb4e3544a95f0f05f66e103ee23b943a76136aa450cf416976ccaeea941978c2c0c70c7cdcc02778560592137ebd5692c71c95ce5453ccb3ca66138318a28c894fe282c0a1ff316f069e34f1143ec59d8ef87e1890a91a6531e849e0d3297c86dd6753f89c89cfe369135fc01779be8efb96e355eb616005337edd2d5b456971bba05e9165ebec8cf42c2708ea3ce396ed59dc3d6be2195c30f02513cfe239fa6ae2cb785ea07fdc73e72ddf9316c3487d5614ac66addaca32157c05174c7c152f50eaba836de26bf8ba896fe045817b4ece48cb955e59d66855d90a392dfab59a7f968492ed797ea83654646a951613ec84f3dcf89bb868e25bb868e0db26be83ef0a640ebbaee54f69deaa025ec9a9b2880556a51e68258133cd021864995813df53867f5f352fe1073d9bf0c3147e64e2c7f889819f9af8197e6ee06513afe017267e895f09dca8a1590f1d9700775da94f81895f6341608f7282def505d69c2a99cb3b7abe37e4c9693b74e6246dbe84cb06164d5c51f1cab5891162e1dad321b06b8353b82476ef1b05636463568b661ba2d98668765934bbcac6a1b6aa08cf681b658481beae02b02a52d1ad26d0352dc315c7d29946add1092d3881aa34eb6b5ff22f383a5120141a1569828a5d39b274594c660a6b6124df54d4f4e5cb32d74eed4ce237f8adc01d99d6e2b846bd4ce276fc4e20df52cedb29b909c79bf36759e71effbfde0afd85593f741d2f7766ae929baa7b0dadc71aa3fdb4a4ab11ea933336c17557e6bf49ace9ce66a67e54174681eed559e7f5e204f757aae1bc7eda9c16d8540f345eb6675a9f46a7d5a322496de3ba2e525d47e09c975a74943748542e83f12975f30becceac91fa16d4c5a94f605b66745ddb0bba3cf2b0675a90e394a3829853319dcf47303fd2a89f02b76cc8ce4433bab61ba8edd740d7e9c8d989a86cf2d5c0c989a6c24a79de4cd2ae08ec5c759e22aa8a1a3b42f255fc5ee0480b9696ad395c0c344a22271a9a0259aad7b4adf5a2eb941e94cabd4d76b5ead2f0db56edb78484652090f3a675cc61c02b76955531b3a182f5dda1b32d4b8dd3eeab2825423f42d6ad6bc56499337a67ea89c0becc469c6b02a34b1d2ddbf102de7a023bd6a93d2a879d4c9b7ec9ab3437eb1af542c9f34b655b5b8814731a3f00065e33f107fcd9c4db71d0c05f4cfc157f13b87d45262a17b9827e54f29d624fd9ca70e6a9abb23233f00f46a7e0fbb375c6ff5fcd886b28889e380fb04cf0a6e98d38f3adc7703d4175eaded862b4e5c6b2fdadab23b6eb4e38faf578edddb136b6f913a6aac7598f6e10d04de7660db41b789d7aaf2b4804dbc67cd8c57b61377f217bf9ed4006fdec07f8b31ac35ec439e6f3956d96941c7bc17ed3c0258857344b8e6d421377621f5b3362c07edcc95ee02dfc198e69618f7d9cfdf6bd0b88a5e397d131b677f00a59711989534a5b5c6bebd65cbd48620fb661586bb522c9865635ba1bf7507b92fb0de35e6a7e6b63ef889227e580b2439011a9a482676486b8c41d3bb8f4ec60da185840e722360b2c203998eee2d45cc41696ee8b303a5e42479cf48174f7027ae28b48c5f01aba8f0fa6b70e2d20cdef8605dcf8c20ae3607a1b3ddbce859b16f126c197dc0e601137c7e8dfce45bc5989dfb2885b63d16eb791d15ac0ae17573488979783700c5bd9f6d1d20c1dea430fb37203b3d2cbbe8f79196656f2cccb18fb13f4eb24a5ceb37f8c017a82417f9afd33f45d056f20f257870c7aa44226f4e810ee635c86f1080ee308f71e21f53924ae12107103470ddc6fd096181b03efb8aacc5ba1c623aab8aaec5c261b78a0997ff5c28ac87ded8ae87c6e89e3ee540ac3fc0ea554ac463508df490b809b39df432cdf91d8ac476fc366fc117fc79f98887769d0c4f010572618ad871b230ffe7f00504b0708a2a28a375f070000b4110000504b030414000808080000004100000000000000000000000000210000006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f0300504b0708000000000200000000000000504b030414000808080000004100000000000000000000000000300000006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d612e636c6173738d4f4d4bc350109c6dd344636c8bffc05b5bc477f1a678118442b0876aef9bd7c5be920f4952f16f79123cf803fc51e2e6b57876178699d9dd81fdfef9fc027085718c3e4e230c238c08e18d2b5d7b4be84fa62b427057ad85304a5d290fbb2293fa91b35c9db3b4b29cafb8769d3e9841bb710de1222da535b6aad76c1a2e5e72698cbc79621abb9182cd7cf1b4f4ec9a102fab5d6de5de7511c3bfc9e5965f3941800161f6ff40c2b83b343997cf66916dc5b638474f7fec8ab43551315465bc0606b30fd0bb921e22c5d09b218e1493fd028e11fbf313bf95fc02504b07088ae07cf1dc0000003e010000504b030414000808080000004100000000000000000000000000400000006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d6156312450657273697374656e74494f552e636c6173739d545d4f134114bdd34f0a454ac58fa2282a62bb7c0c0812838444509326558985fa488676d28ed9ee92dd5984377f900f9ad898f8e00ff04719cf6c5bc0765ff4a13377e6dc73efb9f7cef6d7ef1f3f89689d3646294d4b194ad1b259b85956ccb29aa6b534ad334ad9d269488f51bef2419c086e0ba7c9abda534ef319a3c2bbc0d1aa2d6bca5747b67cee38ae165ab98ecf683a249cf263e9f9cad7d2a94bbeebda41db0131e188b6643472e47a9efbd1c44f9e083bc0152be3da568e145eb9c128d74d1b6865f38383f20b70335df450019eadb85e93b7d491f41ca12517170af8fed9b134a93476b082403596ea2d815ca92de528bdcde86971b8aae19bf2a086520d6177dd06c24e5420e64dd086807d81169846b97561d784a7ccb97799d02d859e8ceff59ba1cb6f0f1865cb8e23bd5d5bf8be04bc5571a4e675d76b08ee8bf6b12d7d2e4f4383fbf5966c0b0e5a35b46aab737f0543a5b9d752b7dcc69ef0d05c0d9051bc68b4669a52577a739c2a96a2263906979df3618ce054ebce03113091242ecc38f27df6e5818c56ddc0abcb57ca549abba470d9b846bf84977837facc3ca108306c9a09acdce0d0c73ca59fa5eb349ba511ca6469dc2c5768224b399a4cd313469bffdf3746f31764ac7d86cf2fdcaa4602a3c57fc942f7f019a5f19525286f6413cac1690cbbf9657d5ce64d29c3c0380094370c5c0180927bc014c5fa409eaec298f2e91a9232b4ea06b09bf0f9843d897ddafa4ecc5ae850cc5aec50dc9ae950c22a243a94fc0a344605e3032ed13c043f82aa22b29510d602b600ccfc5d8491e816dd210aad6e59c63275c442cb088f8796519aa0bbb0271370253811600240a1c859ac46e47b504d984228921991cc888c1b912c42e332e272645c41b855687c8c306ba1c66c37504f23c310eef79270ec064b5adf28f6e53c602abcdcb8444e9e931f4492e383e4cd48f21c3d8c20273e0f90b723c9f318c1303939987927821cc7e48c57297c2313b02cec0bdd77b24833388ce29042d36e53e60f504b0708e139b3c7e70200000a060000504b030414000808080000004100000000000000000000000000320000006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d6156312e636c61737395534d6f1331107d4e42b60d5b1a420ab4e5abb495928ac642e2441052a9841469dba2a644429c9c8d95b8daf546b617957f05271012fc007e1462d6a46de044f730b6c7efcdbc99f1fefcf5ed078067d80e7037c06a80b51ad671af8605dc5fc083000f033c62587a238d55d649ed7a476f19c29ed6d2ec27c25a6919aa2f9456ee2543b9d51e3054f6b39164588e949687793a94e6440c13f234a22c16c94018559c67ce8a9b288ad189b4743ccecc48702bd269222d97677ec36d3c91a9e094baef7783a75d86e658ba033536c2a94c1f4b9be526a670cd563b3a151f044f841ef3be334a8f09bd7a9c6ba75239505651da3dad33e799947add13ceb8b870f2c33c490a79c4acf57de4d7aa105b9fd3d029580c3bffaf9b7a7229cd778fe1f955cadefa6b0e0136423cc66688ebd8a2ca559677e209c5964936de4d05e10cc393ab2460d8bc84933dc7587e20a653393aafa3eeebc89d4af89e31e263f108848d481ac376ebfddc048e86a73276ddd9503ca3805163dbade89f6e747b739e1ea9f723680fb081805e64f195c0a8da90ec129d5e919fd1dadc69b04ae53b4aefca8d72ff2b2a5f70edb347df205ba39530b885152cd32efcc3411d3769a5674937251f6f974ec55db951fd7441af7ad7da1cb53ca33667b72b1e7bdbdb3b94ae48493f03895bc4e26f504b07082be84efeea01000064030000504b030414000808080000004100000000000000000000000000210000006e65742f636f7264612f73616d706c65732f6578616d706c652f7374617465732f0300504b0708000000000200000000000000504b0304140008080800000041000000000000000000000000002f0000006e65742f636f7264612f73616d706c65732f6578616d706c652f7374617465732f494f5553746174652e636c61737395565b57135714fe2609992446c12858b52a2ada10c040d57a09da42d49a360a1aa1a6f63624c7303a998933132b4fed8fe84bff855dab40575db6abaffd515dfdcecc04c885880f9939679f6feffdedcbd9997ffffbf32f0097f0328161e4e338825bf2715b3eeec8c7e72aee2650c0172abe54514c60018b093cc0c3044a7894c012961388e32b158f6328273088af553c4920867c0cdfa8f83681eff0bd8a1f54682a56140cbcd48ca65070a8f84c7ba9650dcdac650ba62b6ac2ce29881ac2ac0a5bc1a9a229dc6cc5b2ab9a7c8aac5e15a6abbb6bd945cd76d7088dad58b66dfd28c1314337856617aa0a263af52a96e9da5ac575b24ba6fea2290a9e9da7baef6e563775f7a6829fd23de8bc83c27b1ef72132beac2092b7aa4ccb6091a1dc6fd65784fd485b31284915ad8a662c6bb62ef78130e2aeea4e7bb48e566f18c2c98a57de22ebb89acb6d6161a924578c76e89e7057ad2ae96975e10a9b066235e12efb05194e8ff72c499c90625095d3c4bcab2efb889fdf2a8ddc15b7aa33d5addfb73e83d49676f58aded04c9784532d964d5737b245dd7125c5925e3335b769338c5c17607657ca732b8ee7dba77e93960ed784296ca6eb9ed66888eac2ca335171152ca43b6d38955551d79cac8f2b79bb5c57702dd422934d2674dbaa45d43f52706e4f9615eca766e5398541070c39cd46c3b2dd1684b91969af202b2ca1d4bdd1f3a02b2f3d3dcbacc45cabe4daba596382da4cf952221225ab6957c41d5d52dbdfeab90b12a9e0e8c326f35d17cbbaa3d3ef9c695a3cd52d939c2777ef8779615866cd7964e50311fdccf469f86d4dfadfd249e2342a491cc3f1243ec489244ecac7298c32f57bea0b15d524049e926b9fcbe625cbbb6cde6a7946c1f5f7818f6db708a5cc61c73e5930d9987943731ce1a8a825b10a5dc5b324667143c5f3240cd45598495868c8985f2838b3a3e686216a9a3167d79a759abcfdaa221ab2020a8e2f99b6a8583553774475d427363ae6bfa51ddee1b37be81305575a554f7b13fec6396772d49fe6deb235ad7d793011b819672b6ff3f42f9c0a2709174d05e37b9e6f0ac676ed247f0005b0ceaab7a279d014f69abc17012e9c966379687b96ccd9b6b6c6968d6a8e1c2bb4947e52eca49eeb319e4ef41d990a544eb9fb1cc90cb7cf7ccd4bd9e3cbd3d3129aebd3bd6d400507bb863a2fb46eb6c63ec32cb4e5f91d5399ffe0a42b8779fb285e5a2adc22ababe9eef1d02d29742aca540ff750dd2ec10e294bf0d4b2eb1a4b70ad87ceee45d989626b1fe1374f081fe0282248c909c14fa1941c12defb64f0e6a8e03b0efefbe10cf167b9fb99ef01be8f6536a16426d611ca4cae239c995a47247334b28e81df781ac298c420cae747f491a695711c4006873041af9338e77d7c7996709e18782bc944f156924bc85b4936616f25f9485bc0c108b720083c060f40b5719a573c9259bea59981ccef08bddee213f584173cdf491f10f8e6f70439752b873b95b33d95a77a2a473a95a77b2a5ff0943a95073a95677a2a4f53ee17e633a6469e8d0cbc45b41c96e44be588a451fa036aa7b58b3bac8d04d63ef6301729bb84cb81d55f889765c84dfc83d8af987a8378599ade406203fba4f5ad55680349497c03fb3771e0f51b0c9653439b38f837d5c39eeb33fc3606ae40c5557e2d5f631f5ca7931ccb36cb40ae32949b1ead11dfe5565fe4f009b578c33c4bca8cd702030aa53205d768c5273bcbc4c8805291b74895c36f102b6fe250aff0f33bc24fb5859fa38cff2b414516038be75387d5b718f6d21af2d3caec7a452e95a3326a7a19e9f472778797f38197306394a84f5930601fcfe6f83b56c13cee5390e026ce34dd43fc7f504b0708751ed2f940050000a20c0000504b01021400140008080800518e9255bd0395cb11020000940400001400000000000000000000000000000000004d4554412d494e462f4d414e49464553542e4d46504b01021400140008080800518e9255f597f2e3300200006b0400001400000000000000000000000000530200004d4554412d494e462f434f524441434f442e5346504b01021400140008080800518e925544c58c2113020000030300001400000000000000000000000000c50400004d4554412d494e462f434f524441434f442e4543504b010214001400080808000000410000000000020000000000000009000000000000000000000000001a0700004d4554412d494e462f504b01021400140008080800000041000000000002000000000000000400000000000000000000000000530700006e65742f504b01021400140008080800000041000000000002000000000000000a00000000000000000000000000870700006e65742f636f7264612f504b01021400140008080800000041000000000002000000000000001200000000000000000000000000c10700006e65742f636f7264612f73616d706c65732f504b01021400140008080800000041000000000002000000000000001a00000000000000000000000000030800006e65742f636f7264612f73616d706c65732f6578616d706c652f504b010214001400080808000000410000000000020000000000000024000000000000000000000000004d0800006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f504b0102140014000808080000004100fb7b2bc11c0100001a0200004500000000000000000000000000a10800006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e747261637424436f6d6d616e6473244372656174652e636c617373504b01021400140008080800000041002b457a09c6000000750100003e00000000000000000000000000300a00006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e747261637424436f6d6d616e64732e636c617373504b0102140014000808080000004100a2a28a375f070000b41100003500000000000000000000000000620b00006e65742f636f7264612f73616d706c65732f6578616d706c652f636f6e7472616374732f494f55436f6e74726163742e636c617373504b01021400140008080800000041000000000002000000000000002100000000000000000000000000241300006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f504b01021400140008080800000041008ae07cf1dc0000003e0100003000000000000000000000000000751300006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d612e636c617373504b0102140014000808080000004100e139b3c7e70200000a0600004000000000000000000000000000af1400006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d6156312450657273697374656e74494f552e636c617373504b01021400140008080800000041002be84efeea010000640300003200000000000000000000000000041800006e65742f636f7264612f73616d706c65732f6578616d706c652f736368656d612f494f55536368656d6156312e636c617373504b010214001400080808000000410000000000020000000000000021000000000000000000000000004e1a00006e65742f636f7264612f73616d706c65732f6578616d706c652f7374617465732f504b0102140014000808080000004100751ed2f940050000a20c00002f000000000000000000000000009f1a00006e65742f636f7264612f73616d706c65732f6578616d706c652f7374617465732f494f5553746174652e636c617373504b05060000000012001200aa0500003c2000000000</td>
<td align="left">Cordapp-example Contracts</td>
<td align="left">2022-12-18 14:00:20.73</td>
<td align="left">app</td>
<td align="left">1</td>
</tr>
</tbody></table>
<p>(1 row, 13 ms)</p>
</li>
<li><p>SELECT * FROM NODE_ATTACHMENTS_CONTRACTS;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">ATT_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">CONTRACT_CLASS_NAME </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">D120F4F7FF3EAEF9D6937E7B6DA8774F1F3F258E44D25AE2EED04D343E61E519</td>
<td align="left">net.corda.samples.example.contracts.IOUContract</td>
</tr>
</tbody></table>
<p>(1 row, 6 ms)</p>
</li>
<li><p>SELECT * FROM NODE_INFO_HOSTS;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">HOST_NAME </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">PORT </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">NODE_INFO_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">HOSTS_ID </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">localhost</td>
<td align="left">10005</td>
<td align="left">1</td>
<td align="left">2</td>
</tr>
<tr>
<td align="left">localhost</td>
<td align="left">10002</td>
<td align="left">3</td>
<td align="left">4</td>
</tr>
<tr>
<td align="left">localhost</td>
<td align="left">10008</td>
<td align="left">5</td>
<td align="left">6</td>
</tr>
</tbody></table>
<p>(3 rows, 5 ms)</p>
</li>
<li><p>SELECT * FROM NODE_TRANSACTIONS;</p>
<table>
<thead>
<tr>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">TX_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">TRANSACTION_VALUE </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">STATE_MACHINE_RUN_ID </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">STATUS </a></th>
<th align="left"><a target="_blank" rel="noopener" href="http://192.168.3.159:8082/query.do?jsessionid=882f26be2f2312cc47b2d15f2c2188d7#">TIMESTAMP </a></th>
</tr>
</thead>
<tbody><tr>
<td align="left">45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2</td>
<td align="left">636f72646101000201ff060000734e61507059001f0f00b5e6f849a95914000080c562000101e001d000002c990000000300a3226e65742e636f7264613a7a546f494c693843672b7a39514735324473465439673d3dd00000235c00000002002e2e0054736e2f586467386d5964443655614875684174667541052e0801d6003e2e007479765a4541456b2f4d6f6c336741313131356d6775513d3dc0c20400a3211984f0876a6176612e73656375726974792e5075626c69634b6579a02c302a300506032b65700321008554bcf8a392ea690f53a10c1c2af60c8f88900b00a3ac012ce5a87162a2a76da040527135bf9e729efcf8e1dc6d3f175a6d932af6e0276833c745811e1501018a1abab50b70ecce511f47e990c85118e1c227a4dd42cee4154b8495551c09ba280d4032190178497a46743863524b7974734a713376512b796a7347673d3dc00502540b5404322c00fee90032e900f063cbe236e9fa600881d58cf9f8fed832c36691150cb9cdfceec32eea3a9342cbb7a040654ede554661888802bd8fae1f90f75347d5d01ad42c1b3e53464361f35bbb0dd0ac98f54b839ca48fccbec417418a86728c8c04bb7352550ee9afe3acaa820d40002ed401aee90054433554516952424f4541662b4b4f31317a546a555051450028212e00000001b000002125455a040100367c0204210e427c0254624d594c503062515854394567324c74664242395267054e041b26422e0050534c7758304d6874704f6f574f714c2f42646a2f76097c141a7d0000000632930150486e6553504138394d476870697a564c453377634f095c000e018a36d802544a597065626c59374372782f61314a6968784a433677058a040dde01d8325c00504c5935355955446a784f38344f6c775377557a76536906040db0012e10b000000da7520601040d9042d8005051307a55474e2f4b367777777975496c4e66335261097c14037600000005327c0068372b30747468524e384b742b546255446266663837413d3dc082019254033c5b3059301306072a8648ce3d020106080509f04803010703420004038d226dcd0fa574316da478aa75225e6ce18f65cbd96e60bf3c8251b196541756e5dcf7ccab21b712601ed0278501f2f33d0b5fdaa4c09e62639464e4910871a12f75d4282e73616d706c65732e65780509382e636f6e7472616374732e494f55430d0d32da00504465436e735363676e506a582f45576e305369474929561001b40000003673035048394b4f69386167557573674b4b69334d45423378619f009436da01446e6764776274366b5254306c356e6e3136752d30681a0640a1025553a1084e657720596f726ba1065061727479424040924901329d047eb40332e90062bb0000929abb00001801bb244742a1064c6f6e646f6e0db90041ceb9007e560532b9004c726e69773742324d7169377a6c6b50704b6d4a37457c5813024098d68e6752f1a84f7c8b25e875a2a18cab543240323d00fef60046f600144e6f74617279cef6007c0ce784a56bed60f71e348bc81e557796b777183c8d3a50ecd5f3ae0ec720135af5351402d0000009d061d3010910c70000000a151c1405d00000018461a104a12959f808636f722eed02445472616e73616374696f6e5374617465404515400c03c026022e88055e080400400168001c0168153b5c04c04607a10a636f6e73747261696e74a1012ac03001a12d628700284174746163686d656e744315350c404041421d520c1807a10871a520a106737472696e67453a24001c3907a1046461746101700c2901a12662700071e109f4426900500b656e63756d6272616e6365a103696e74454040422e8d00102d07a1066e25df04a11d3a6500106964656e7412280861ae36a2000c05c09605be0601c6390135353ec2015c4d6766362f7332416a6b5a6154382f6255396e4e53513d3d3df50c05c08805a23801aa64016294004c5a326932426d6f35324566756346585a38423243e1b232940004d1057a67011d2e3ef5005ed8030c40c07b0215962c04c03307a1046e616d65a1255ed00100430e900a1c583530304e616d6536d8013804c02f07a1096f776e696e674b6579417f0c1a01a1175a380a32700265a60044613e9a7a006aeb005e4c060c40c0e3061deb001a659c0c6d6d6f6e01ca7d4c32e302281707a107636f756e7472791d23429303186c6f63616c69746224002c1c07a10c6f7267616e69736181665e4c000c2007a1102e280008556e692ee703329b00101507a1057381ae1d4d1d211405c0d605a1363ac701913b28732e5369676e6174757265527504fe6f037d6f5e0b090c40c036013d8f102907a1036bca350200b64535bddb3ed308252312d00889e710c07603a124621701144c696e656172052a9e010442b20240736368656d61732e517565727961626c65054f15ec3e9b035e52090c40c0da041535655c2008626f72726f7765727a08044ea8050c6c656e64c23900103b07a1086c25120449642e64013a3f0718556e6971756549a5f30c666965723e17041c1207a10576616c754e46060c05c0ac059690010c40c04f02962a009eba01355e3e930154416a4d5a704d6f6a5268685a36364a6b7433576243413a230600ae46ac0456fa010c40c050029a2502eeba0005ba5442383263534636543034544350666c67587332626b673aba0000a56e0c093ecd016a6a055e6a0a0840c0432e5506a16a2465787465726e616c496456ae043404c01007a1026964a104757569643641021009c101005436dc0d6a380e04032442e2106a380e0402f40e370a32030b6a380e0402c6012e10b0000002bd52380e0402a646380e484249645a30386e4f6a4e6334755154395a4e540e020d26620a0ebe0a040260015910d00000025705421e0f121405c0d905a13f99ae3edd04b9d02ab00d3024436f6d6d616e6473244372650ece0a10c06102a138de45006a73030d680c4461746115b23e4b035e00015d570c05c0d205e6a000fede00f2de0054473671693569446234552f4b6b5071344e6531494f773a6f0300846ee1043d440c40c02701fa6e015066713652502f6633746a44686f6a3059783669704136ff03654e36c30e6a4e03040171ae4e0304014141c79e4e03040113012e10b00000010a464e0304c0f63602155037595a535555337443365976745833334b6c6f394a0e4a10902301a020d120f4f7ff3eaef9d6937e7b6da8774f1f3f258e44d25ae2eed04d343e61e5190071501402c09201c08f2678081405c08205a127791bc9d918727970746f2e530eeb142c6548617368245348413235365db33ee6025e9e000840c022196d000412b3092c6279746573a10662696e6172e1aa044142753c259b36f7006a9b01040394ae9b01040364216d9e9b01040336012e10b00000032d469b0110d00000031685a72e190f5e620ce63011fe3a109a3a1004023d01eca17c00342551512c0005fe710dfe710dfe710dfe710dfe710dfe710dfe710dfe710dba710d65be3aff1466df160401d5456d2e42036aa7080401a541a4322e00004c66df16040177012ea159006e52be0300011665082e7c005031424c504a674e7673786476506362724951643837a15f04a502c6681586af14be571a82ba1571b51402c06e01c06bb9741406c05e06a120128310247574696c2e4c6973743c050f486c616e672e4f626a6563743e4045a1046c69736634125e1f01dd1325ffa2de18fe5807fe58079a58077c86f50e03291093da194b19f7f7c0adc68bbb052000006c7699641869d5f8fe003977fe5807fe5807825807000832f002906a515857596833364c31584b644f7836486b533070773d3dc00a01a1075348412d323536003221034c736b5566426163553141676d4c58384d317a38330ed2190e80087c3cb6e446ba7616381fcbe3b6bcc0a062e1479bbc2e1d59a63433b20b1f513a78392810d00000059e619e0109109500000008151c120413619a0805a12b3a9208007426a01614732e576972652ab1165d833e96085eba1b0c40c0f00315775004c05807a10f636f6d706f6e656e7447726f7570730ebc13083d01a116f41d79396e97000043324200003e32df135004c03a07a10d64696765737453657276696365a1233a4d001a760900442e250036080e00040eda162c0b7072697661637953616c746a2d0b005019263645000c06c07806f2d80000457a2b045e011d3da81405c0e205a12a3a000132e401364d011d3b3ee3015e62060840c07f2e830f004d16ed1429e325de0c3701a134a50862de0101193069746965732e4f7061717565420eb90a3ed801101907a10a67413310496e64657816261808a101302ed60a0c06c07206da6c007e6c015e32073d310805c07f467f0d52db001d353e660150706754304b6333742f62766e7a6d67752f6e6234430e570db2df0b0c05c0860592f7026a8a005eb8040840c02ad9f54804c01d07a10d68617368416c676f726974686d2a76112a710c521d012654107d456a93005e1a05be1d010c8705a12c3a14031c73657269616c697a123417042e530d0e046564458b6a93005e1c09b69300e1d2b527a1ba0408f3adba0408ea46641c00971289163edd1b32d6030e74170465642ebc0510c05e02a1353af5003233001d2d0c57697468014212b6176e97110ed018086442790eba0e15bf3ed2025e51240840c0cf3a38040c047369678532861006adc31db415b03e38042c6907a106747842697473a1593a000172f5017a8306321a07003e36fa050c05c0cc05da6d01fea801e6a80150326e41485a354f6d49724e6c6a366c494972485545b261125d0e7a61121d2a62380250744a78774e6b75764b72494276646c7261624a4a56363d1d8e6207722a027ef60500735adf269d11124c0969923e68076a7b001440c03e01a13be516006c0e1e0ce1860461720ec2193e7702d941818b2053657175656e63653e6237015e7b260840c0f22ee419102807a10262b2391d8254125804c04207a1117061727469616c4d65726b6c65547265655ef5120eaf1f3229003e4c1a014e00731e3c1c0c4d657461126a205e43133e29003e920304b205f27001feb10166b10150376d6e457053616e397a556b7538316f563658786e3e780304ae055ef9004247015d9c3e8b0550515a464f3473386e672f6a6e654f7836614339352f615304c04e2ed307244107a104726f6f74a1333a30054dd142730000240d1221ef3e7801046b05d247006ac60050716f4c4c6843593137505a77564e523645577866420e230926e9180805c0b4623101422a021d383e31015e0b290840c0542ebc06481e07a10f706c6174666f726d56657273696f6e52a00a122e09000e12bb1b20654e756d62657249445229000c05c0f305feae066aae06fecd0266cd025e102ac60f09</td>
<td align="left">bef80db1-615f-4981-91d7-50bed6a47e5c</td>
<td align="left">V</td>
<td align="left">2022-12-18 14:22:35.67</td>
</tr>
</tbody></table>
<p>(1 row, 6 ms)</p>
<p> you will see one row. The state machine id is that of the machine that ran the creation <a target="_blank" rel="noopener" href="https://github.com/corda/corda/blob/67e3e09a4edb41d17b8adfa669d671c690c5db33/core/src/main/kotlin/net/corda/core/internal/FlowStateMachine.kt#L41">flow</a> of this transaction. </p>
</li>
</ol>
<h3 id="Confirm-your-IOU"><a href="#Confirm-your-IOU" class="headerlink" title="Confirm your IOU"></a>Confirm your IOU</h3><p>Turn your attention from the database to PartyA’s interactive shell:</p>
<p>Copy</p>
<figure class="highlight yaml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line"><span class="string">Sun</span> <span class="string">Dec</span> <span class="number">18</span> <span class="number">22</span><span class="string">:37:07</span> <span class="string">CST</span> <span class="number">2022</span><span class="string">&gt;&gt;&gt;</span> <span class="attr">run vaultQuery contractStateType:</span> <span class="string">net.corda.samples.example.states.IOUState</span></span><br><span class="line"><span class="attr">states:</span></span><br><span class="line"><span class="bullet">-</span> <span class="attr">state:</span></span><br><span class="line">    <span class="attr">data:</span> <span class="type">!&lt;net.corda.samples.example.states.IOUState&gt;</span></span><br><span class="line">      <span class="attr">value:</span> <span class="number">50</span></span><br><span class="line">      <span class="attr">lender:</span> <span class="string">&quot;O=PartyA, L=London, C=GB&quot;</span></span><br><span class="line">      <span class="attr">borrower:</span> <span class="string">&quot;O=PartyB, L=New York, C=US&quot;</span></span><br><span class="line">      <span class="attr">linearId:</span></span><br><span class="line">        <span class="attr">externalId:</span> <span class="literal">null</span></span><br><span class="line">        <span class="attr">id:</span> <span class="string">&quot;d68e6752-f1a8-4f7c-8b25-e875a2a18cab&quot;</span></span><br><span class="line">    <span class="attr">contract:</span> <span class="string">&quot;net.corda.samples.example.contracts.IOUContract&quot;</span></span><br><span class="line">    <span class="attr">notary:</span> <span class="string">&quot;O=Notary, L=London, C=GB&quot;</span></span><br><span class="line">    <span class="attr">encumbrance:</span> <span class="literal">null</span></span><br><span class="line">    <span class="attr">constraint:</span> <span class="type">!&lt;net.corda.core.contracts.SignatureAttachmentConstraint&gt;</span></span><br><span class="line">      <span class="attr">key:</span> <span class="string">&quot;aSq9DsNNvGhYxYyqA9wd2eduEAZ5AXWgJTbTEw3G5d2maAq8vtLE4kZHgCs5jcB1N31cx1hpsLeqG2ngSysVHqcXhbNts6SkRWDaV7xNcr6MtcbufGUchxredBb6&quot;</span></span><br><span class="line">  <span class="attr">ref:</span></span><br><span class="line">    <span class="attr">txhash:</span> <span class="string">&quot;45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2&quot;</span></span><br><span class="line">    <span class="attr">index:</span> <span class="number">0</span></span><br><span class="line"><span class="attr">statesMetadata:</span></span><br><span class="line"><span class="bullet">-</span> <span class="attr">ref:</span></span><br><span class="line">    <span class="attr">txhash:</span> <span class="string">&quot;45C9C2FEF670D89289D8E02BADBF34854F8C56ADB624F4B524A5F7AE8FF944A2&quot;</span></span><br><span class="line">    <span class="attr">index:</span> <span class="number">0</span></span><br><span class="line">  <span class="attr">contractStateClassName:</span> <span class="string">&quot;net.corda.samples.example.states.IOUState&quot;</span></span><br><span class="line">  <span class="attr">recordedTime:</span> <span class="string">&quot;2022-12-18T14:22:35.685Z&quot;</span></span><br><span class="line">  <span class="attr">consumedTime:</span> <span class="literal">null</span></span><br><span class="line">  <span class="attr">status:</span> <span class="string">&quot;UNCONSUMED&quot;</span></span><br><span class="line">  <span class="attr">notary:</span> <span class="string">&quot;O=Notary, L=London, C=GB&quot;</span></span><br><span class="line">  <span class="attr">lockId:</span> <span class="literal">null</span></span><br><span class="line">  <span class="attr">lockUpdateTime:</span> <span class="literal">null</span></span><br><span class="line">  <span class="attr">relevancyStatus:</span> <span class="string">&quot;RELEVANT&quot;</span></span><br><span class="line">  <span class="attr">constraintInfo:</span></span><br><span class="line">    <span class="attr">constraint:</span></span><br><span class="line">      <span class="attr">key:</span> <span class="string">&quot;aSq9DsNNvGhYxYyqA9wd2eduEAZ5AXWgJTbTEw3G5d2maAq8vtLE4kZHgCs5jcB1N31cx1hpsLeqG2ngSysVHqcXhbNts6SkRWDaV7xNcr6MtcbufGUchxredBb6&quot;</span></span><br><span class="line"><span class="attr">totalStatesAvailable:</span> <span class="number">-1</span></span><br><span class="line"><span class="attr">stateTypes:</span> <span class="string">&quot;UNCONSUMED&quot;</span></span><br><span class="line"><span class="attr">otherResults:</span> []</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="string">Sun</span> <span class="string">Dec</span> <span class="number">18</span> <span class="number">22</span><span class="string">:37:11</span> <span class="string">CST</span> <span class="number">2022</span><span class="string">&gt;&gt;&gt;</span></span><br></pre></td></tr></table></figure>



<h3 id="more-command"><a href="#more-command" class="headerlink" title="more command"></a>more command</h3><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">Sun Dec 18 22:37:11 CST 2022&gt;&gt;&gt; run registeredFlows</span><br><span class="line">- &quot;net.corda.core.flows.ContractUpgradeFlow$Authorise&quot;</span><br><span class="line">- &quot;net.corda.core.flows.ContractUpgradeFlow$Deauthorise&quot;</span><br><span class="line">- &quot;net.corda.core.flows.ContractUpgradeFlow$Initiate&quot;</span><br><span class="line">- &quot;net.corda.samples.example.flows.ExampleFlow$Initiator&quot;</span><br></pre></td></tr></table></figure>



<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">Sun Dec 18 22:38:17 CST 2022&gt;&gt;&gt; run partiesFromName query: Party, exactMatch: false</span><br><span class="line">- &quot;O&#x3D;PartyA, L&#x3D;London, C&#x3D;GB&quot;</span><br><span class="line">- &quot;O&#x3D;PartyB, L&#x3D;New York, C&#x3D;US&quot;</span><br><span class="line"></span><br></pre></td></tr></table></figure>



<h3 id="Create-your-third-IOU"><a href="#Create-your-third-IOU" class="headerlink" title="Create your third IOU"></a>Create your third IOU</h3><p><a target="_blank" rel="noopener" href="https://training.corda.net/getting-started/look-into-the-database/">https://training.corda.net/getting-started/look-into-the-database/</a></p>
<p>Again, you will use PartyA as the lender, but PartyC will now be the borrower. This time, you are going to experiment with a checkpointed state machine. You will remember that a checkpoint happens when a flow is waiting for something coming from elsewhere. In the IOU case, PartyA has to wait for PartyC to return the transaction it signed. It is at this point that PartyA will checkpoint. PartyA will checkout whether PartyC is running or stopped.</p>
<p>However, for PartyA’s checkpointed state to last long enough for you to see it, you will first stop PartyC. Type <code>bye</code> into PartyC’s shell. While you are at it, also stop the Notary.</p>
<p>Copy</p>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment"># On PartyC:</span></span><br><span class="line">&gt;&gt;&gt; <span class="built_in">bye</span></span><br><span class="line"><span class="comment"># On Notary:</span></span><br><span class="line">&gt;&gt;&gt; <span class="built_in">bye</span></span><br></pre></td></tr></table></figure>

<p>Now back in PartyA’s shell:</p>
<p>Copy</p>
<figure class="highlight yaml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="string">&gt;&gt;&gt;</span> <span class="string">flow</span> <span class="string">start</span> <span class="string">ExampleFlow$Initiator</span> <span class="attr">iouValue:</span> <span class="number">20</span><span class="string">,</span> <span class="attr">otherParty:</span> <span class="string">&quot;O=PartyC, L=Paris, C=FR&quot;</span></span><br><span class="line">       <span class="string">Generating</span> <span class="string">transaction</span> <span class="string">based</span> <span class="string">on</span> <span class="string">new</span> <span class="string">IOU.</span></span><br><span class="line">       <span class="string">Verifying</span> <span class="string">contract</span> <span class="string">constraints.</span></span><br><span class="line">       <span class="string">Signing</span> <span class="string">transaction</span> <span class="string">with</span> <span class="string">our</span> <span class="string">private</span> <span class="string">key.</span></span><br><span class="line">       <span class="string">Gathering</span> <span class="string">the</span> <span class="string">counterparty&#x27;s</span> <span class="string">signature.</span></span><br><span class="line">          <span class="string">Collecting</span> <span class="string">signatures</span> <span class="string">from</span> <span class="string">counterparties.</span></span><br><span class="line">            <span class="string">Verifying</span> <span class="string">collected</span> <span class="string">signatures.</span></span><br></pre></td></tr></table></figure>

<p>It remains stuck at <code>Collecting signatures from counterparties</code>. That makes sense because PartyC is down. You will note that the steps are made explicit <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L40-L43">in the code</a> itself.</p>
<p>Do not interrupt PartyA’s flow. Return to your H2 console connected to PartyA and run the following queries:</p>
<ul>
<li><code>SELECT * FROM IOU_STATES</code>, no new IOU, only the previous one. The transaction proposal is still in PartyA’s message queue so, nothing has been persisted.</li>
<li><code>SELECT * FROM NODE_CHECKPOINTS</code> returns 1 line. Interesting. This is what happened when the initiator flow <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L112-L113">handed over to the responder flow</a> on the other party. The state machine was checkpointed to disk, and the flow is in effect, <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/cordapp-example/workflows-java/src/main/java/com/example/flow/ExampleFlow.java#L80">suspended</a>.</li>
</ul>
<p>Ok, start PartyC again. You will start the individual node from the <code>workflows-java/build/nodes</code> folder that was created by <code>./gradle deployNodes</code>.</p>
<p>ShellPowershell</p>
<p>Copy</p>
<figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">$</span><span class="bash"> <span class="built_in">cd</span> workflows-java/build/nodes/PartyC</span></span><br><span class="line"><span class="meta">$</span><span class="bash"> java -jar corda.jar</span></span><br></pre></td></tr></table></figure>

<p> Troubleshooting</p>
<p>Back to PartyA’s shell. It takes perhaps a minute for it to retry again and finish the flow. Notice how it also went through the “Notary” parts even though the notary is down. Indeed, the transaction proposal has no input states so no Notary is involved.</p>
<p>Again, you can go to your H2 console and confirm the new state has been persisted and there is no longer any node checkpoint.</p>
<h2 id="No-Notary-validate"><a href="#No-Notary-validate" class="headerlink" title="No Notary validate"></a>No Notary validate</h2><p>You have seen that the notary was not contacted on the creation of the IOU. And, since you have yet no flow that consumes an input state, you have no way of observing the notary’s inner workings.</p>
<p>What if you said the notary should also be <code>validating</code>? In <code>workflows-java/build.gradle</code>:</p>
<p><img src="https://training.corda.net/getting-started/notary_verifying_true_1.png" alt="Verifying notary"></p>
<p>Make the change, be sure your working directory is <code>samples/cordapp-example</code> and recreate the nodes with <code>./gradlew --build-file workflows-java/build.gradle deployNodes</code></p>
<p>The notary was not contacted (not needed), even when the notary is <code>validating: true</code>. Why is that? <strong>Recall that the Notary proves the uniqueness of the transaction inputs to ensure they can be consumed only once. There were no inputs in <em>this</em> transaction, so the notary was not consulted.</strong></p>
<h2 id="关于responder类"><a href="#关于responder类" class="headerlink" title="关于responder类"></a>关于responder类</h2><p><a target="_blank" rel="noopener" href="https://training.corda.net/your-first-cordapp/solution-flows-issue/">https://training.corda.net/your-first-cordapp/solution-flows-issue/</a></p>
<h3 id="Initiator"><a href="#Initiator" class="headerlink" title="Initiator"></a><code>Initiator</code></h3><h4 id="The-class-declaration"><a href="#The-class-declaration" class="headerlink" title="The class declaration"></a>The class declaration</h4><p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@InitiatingFlow</span></span><br><span class="line"><span class="meta">@StartableByRPC</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">static</span> <span class="class"><span class="keyword">class</span> <span class="title">InitiatorFlow</span> <span class="keyword">extends</span> <span class="title">FlowLogic</span>&lt;<span class="title">SignedTransaction</span>&gt; </span>&#123;</span><br></pre></td></tr></table></figure>

<ul>
<li>It has to extend <code>FlowLogic</code> to be considered as a flow.</li>
<li>It makes sense to call it <code>InitiatorFlow</code> as it is indeed an <code>@InitiatingFlow</code> one.</li>
<li>It can be reasonably expected to be started from another part of the system, like the node shell, so it is annotated with <code>@StartableByRPC</code>.</li>
<li>The primary purpose of this flow is to create an <code>Issue</code> transaction, so it is natural to expect it to return a <code>SignedTransaction</code>.</li>
</ul>
<blockquote>
<p>Does a flow always return a <code>SignedTransaction</code>?</p>
</blockquote>
<p>No, a flow can return any type of data, <a target="_blank" rel="noopener" href="https://github.com/corda/samples-java/blob/a61e2cc9910d7d5de83122bf7d36fd071796a7c3/Basic/flow-database-access/workflows-java/src/main/java/net/corda/samples/flowdb/AddTokenValueFlow.java#L17">including <code>Void</code></a>. Your flow could also encapsulate a complex <a target="_blank" rel="noopener" href="https://github.com/corda/samples/blob/e0052bfc491b9133110618a3f6046498a6f25cbb/flow-db/src/main/kotlin/com/flowdb/Flows.kt#L52-L60">vault query</a> or calls to <a target="_blank" rel="noopener" href="https://github.com/corda/samples/blob/f6d9e6a5e8f9d38e597be9f661725610020dd666/flow-http/workflows-java/src/main/java/com/flowhttp/HttpCallFlow.java#L27-L28">third-party APIs</a>, and return the data type fetched.</p>
<blockquote>
<p>Will my transaction be finalized if the flow does not return it?</p>
</blockquote>
<p>If you called <code>FinalityFlow</code> in your flow, then your transaction is finalized. The return type of your flow has no relevance to finality.</p>
<h4 id="The-fields"><a href="#The-fields" class="headerlink" title="The fields"></a>The fields</h4><p>To be able to run its operations, the flow needs some parameters as mentioned earlier. These are passed in the constructor. Here, we pass the <code>Party lender</code> and <code>int amount</code>. Both implementations are equally fine.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">private</span> <span class="keyword">final</span> <span class="keyword">int</span> amount;</span><br><span class="line"><span class="keyword">private</span> <span class="keyword">final</span> Party lender;</span><br></pre></td></tr></table></figure>

<h4 id="The-constructors"><a href="#The-constructors" class="headerlink" title="The constructors"></a>The constructors</h4><p>This explains the main constructor:</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@InitiatingFlow</span></span><br><span class="line"><span class="meta">@StartableByRPC</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">static</span> <span class="class"><span class="keyword">class</span> <span class="title">InitiatorFlow</span> <span class="keyword">extends</span> <span class="title">FlowLogic</span>&lt;<span class="title">SignedTransaction</span>&gt; </span>&#123;</span><br><span class="line"></span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> <span class="keyword">int</span> amount;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">final</span> Party lender;</span><br><span class="line"></span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">InitiatorFlow</span><span class="params">(<span class="keyword">int</span> amount, Party lender)</span> </span>&#123;</span><br><span class="line"></span><br><span class="line">        <span class="keyword">this</span>.amount = amount;</span><br><span class="line">        <span class="keyword">this</span>.lender = lender;</span><br><span class="line"></span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>With this preparation done, it is time to move on to the <code>call</code> function that starts the flow.</p>
<h4 id="call"><a href="#call" class="headerlink" title="call"></a><code>call</code></h4><p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Suspendable</span></span><br><span class="line"><span class="meta">@Override</span></span><br><span class="line"><span class="function"><span class="keyword">public</span> SignedTransaction <span class="title">call</span><span class="params">()</span> <span class="keyword">throws</span> FlowException </span>&#123;</span><br></pre></td></tr></table></figure>

<p>Not much to say about it, other than to draw your attention once more to the <code>@Suspendable</code> annotation picked up by Quasar’s agent.</p>
<p>From there, the flow fetches the identity of the notary and the node running the flow.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">final</span> Party notary = getServiceHub().getNetworkMapCache().getNotary(CordaX500Name.parse(<span class="string">&quot;O=Notary,L=London,C=GB&quot;</span>));</span><br><span class="line"></span><br><span class="line">Party me = getOurIdentity();</span><br></pre></td></tr></table></figure>

<p>And with this, it is time to generate the transaction. For this, we need to create a new Issue Command object. Remember, that our Contract expects a Command.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// Generate an unsigned transaction</span></span><br><span class="line">Party me = getOurIdentity();</span><br><span class="line">IOUState state = <span class="keyword">new</span> IOUState(amount, lender, me);</span><br><span class="line"><span class="comment">// Step 2. Create a new issue command.</span></span><br><span class="line"><span class="comment">// Remember that a command is a CommandData object and a list of CompositeKeys</span></span><br><span class="line">List&lt;PublicKey&gt; listOfKeys = <span class="keyword">new</span> ArrayList&lt;&gt;();</span><br><span class="line">listOfKeys.add(state.getLender().getOwningKey());</span><br><span class="line">listOfKeys.add(state.getBorrower().getOwningKey());</span><br><span class="line"><span class="keyword">final</span> Command&lt;Issue&gt; issueCommand = <span class="keyword">new</span> Command&lt;&gt;(<span class="keyword">new</span> Issue(), listOfKeys);</span><br></pre></td></tr></table></figure>

<p>After this, you create a transaction builder and specify the notary that you fetched before.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// Step 3. Create a new TransactionBuilder object.</span></span><br><span class="line"><span class="keyword">final</span> TransactionBuilder builder = <span class="keyword">new</span> TransactionBuilder(notary);</span><br><span class="line"></span><br><span class="line"><span class="comment">// Step 4. Add the iou as an output states, as well as a command to the transaction builder.</span></span><br><span class="line">builder.addOutputState(state, IOUContract.IOU_CONTRACT_ID);</span><br><span class="line">builder.addCommand(issueCommand);</span><br></pre></td></tr></table></figure>

<p>With the transaction ready, the flow checks whether it is valid:</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">builder.verify(getServiceHub());</span><br></pre></td></tr></table></figure>

<p>You will notice that the verification is done on the transaction builder. This builder does not store any signature, by design. A signature signs a finished transaction, so you would need the builder to first create the transaction before being able to sign it. You will recall that the contract verifies the presence of required signers, not the presence of signatures. That’s why the verification passes even before the transaction was signed. Now, it signs the transaction. (The node running the Flow is signing the transaction here)</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">final</span> SignedTransaction ptx = getServiceHub().signInitialTransaction(builder);</span><br></pre></td></tr></table></figure>

<p>Now, the flow requires the signature of the other parties.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// Step 6. Collect the other party&#x27;s signature using the CollectSignaturesFlow.Each required signer will need to</span></span><br><span class="line"><span class="comment">// respond by invoking its own SignTransactionFlow subclass to check the transaction (by implementing the checkTransaction method)</span></span><br><span class="line"><span class="comment">// and provide their signature if they are satisfied.</span></span><br><span class="line">List&lt;Party&gt; otherParties = <span class="keyword">new</span> ArrayList&lt;Party&gt;();</span><br><span class="line">otherParties.add(state.getLender());</span><br><span class="line">otherParties.add(state.getBorrower());</span><br><span class="line">otherParties.remove(getOurIdentity());</span><br><span class="line"></span><br><span class="line"><span class="comment">// Collect all of the required signatures from other Corda nodes using the CollectSignaturesFlow</span></span><br><span class="line">List&lt;FlowSession&gt; sessions = <span class="keyword">new</span> ArrayList&lt;&gt;();</span><br><span class="line"><span class="keyword">for</span> (Party otherParty: otherParties) &#123;</span><br><span class="line">    sessions.add(initiateFlow(otherParty));</span><br><span class="line">    &#125;</span><br><span class="line">SignedTransaction stx = subFlow(<span class="keyword">new</span> CollectSignaturesFlow(ptx, sessions));</span><br></pre></td></tr></table></figure>

<h4 id="Finalisation"><a href="#Finalisation" class="headerlink" title="Finalisation"></a>Finalisation</h4><p>With this, you could now finalize the transaction.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// Step 7. Assuming no exceptions, we can now finalise the transaction</span></span><br><span class="line"><span class="keyword">return</span> subFlow(<span class="keyword">new</span> FinalityFlow(stx, sessions));</span><br></pre></td></tr></table></figure>

<p>This is the end of the initiating flow, it is time to move to the responder flow, which needs to dance to the initiator’s tune. Notice how here too it instantiated <code>FinalityFlow</code>, and then asked it to run on the node with <code>subFlow</code>. Two steps again.</p>
<h3 id="Responder"><a href="#Responder" class="headerlink" title="Responder"></a><code>Responder</code></h3><p>This will thankfully be short as it does not do much.</p>
<h4 id="The-class-declaration-1"><a href="#The-class-declaration-1" class="headerlink" title="The class declaration"></a>The class declaration</h4><p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@InitiatedBy(IOUIssueFlow.InitiatorFlow.class)</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">static</span> <span class="class"><span class="keyword">class</span> <span class="title">ResponderFlow</span> <span class="keyword">extends</span> <span class="title">FlowLogic</span>&lt;<span class="title">SignedTransaction</span>&gt; </span>&#123;</span><br></pre></td></tr></table></figure>

<p>Nothing that should surprise you at this stage.</p>
<h4 id="The-field"><a href="#The-field" class="headerlink" title="The field"></a>The field</h4><p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">private</span> <span class="keyword">final</span> FlowSession flowSession;</span><br><span class="line"><span class="keyword">private</span> SecureHash txWeJustSigned;</span><br></pre></td></tr></table></figure>

<p>It only needs to know who has initiated the flow.</p>
<h4 id="The-constructor"><a href="#The-constructor" class="headerlink" title="The constructor"></a>The constructor</h4><p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="title">ResponderFlow</span><span class="params">(FlowSession flowSession)</span></span>&#123;</span><br><span class="line">    <span class="keyword">this</span>.flowSession = flowSession;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>Now, we define the checkTransaction method</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Override</span></span><br><span class="line">    <span class="function"><span class="keyword">protected</span> <span class="keyword">void</span> <span class="title">checkTransaction</span><span class="params">(SignedTransaction stx)</span> </span>&#123;</span><br><span class="line">        requireThat(req -&gt; &#123;</span><br><span class="line">            ContractState output = stx.getTx().getOutputs().get(<span class="number">0</span>).getData();</span><br><span class="line">            req.using(<span class="string">&quot;This must be an IOU transaction&quot;</span>, output <span class="keyword">instanceof</span> IOUState);</span><br><span class="line">            <span class="keyword">return</span> <span class="keyword">null</span>;</span><br><span class="line">        &#125;);</span><br><span class="line">        <span class="comment">// Once the transaction has verified, initialize txWeJustSignedID variable.</span></span><br><span class="line">        txWeJustSigned = stx.getId();</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<p>Now, to respond to the CollectSignatureFlow, we must sign the transaction if we are satisfied with it.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// Create a sign transaction flows</span></span><br><span class="line">SignTxFlow signTxFlow = <span class="keyword">new</span> SignTxFlow(flowSession);</span><br><span class="line"></span><br><span class="line"><span class="comment">// Run the sign transaction flows to sign the transaction</span></span><br><span class="line">subFlow(signTxFlow);</span><br></pre></td></tr></table></figure>

<p>As the initiator flow had called the Finality Flow, we now call the ReceiveFinalityFlow.</p>
<p>Copy</p>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">return</span> subFlow(<span class="keyword">new</span> ReceiveFinalityFlow(flowSession, txWeJustSigned));</span><br></pre></td></tr></table></figure>


            </div>
        
        <footer class="article-footer">
        </footer>
    </div>
</article>


    
<nav id="article-nav">
    
        <a href="/gitee-internal-blog/2023/03/09/DLT/Ledger/Corda/1-Corda%E4%BE%8B%E5%AD%90/" id="article-nav-newer" class="article-nav-link-wrap">
            <strong class="article-nav-caption">Newer</strong>
            <div class="article-nav-title">
                
                    1-Corda例子
                
            </div>
        </a>
    
    
        <a href="/gitee-internal-blog/2023/02/04/DLT/%E6%A6%82%E5%BF%B5%E5%92%8C%E6%A1%86%E6%9E%B6/1-%E5%8C%BA%E5%9D%97%E9%93%BE%E7%90%86%E8%AE%BA%E5%9F%BA%E7%A1%80/" id="article-nav-older" class="article-nav-link-wrap">
            <strong class="article-nav-caption">Older</strong>
            <div class="article-nav-title">1-区块链理论基础</div>
        </a>
    
</nav>





    
    




<!-- baidu url auto push script -->
<script type="text/javascript">
    !function(){var e=/([http|https]:\/\/[a-zA-Z0-9\_\.]+\.baidu\.com)/gi,r=window.location.href,o=document.referrer;if(!e.test(r)){var n="//api.share.baidu.com/s.gif";o?(n+="?r="+encodeURIComponent(document.referrer),r&&(n+="&l="+r)):r&&(n+="?l="+r);var t=new Image;t.src=n}}(window);
</script>     
</section>
        </div>
        <footer id="footer">
    <div class="outer">
        <div id="footer-info" class="inner">
            Johnny &copy; 2023 
            <a rel="license noopener" target="_blank" href="http://creativecommons.org/licenses/by-nc-nd/4.0/"><img alt="Creative Commons License" style="border-width:0" src="https://i.creativecommons.org/l/by-nc-nd/4.0/80x15.png" /></a>
            <br> Powered by <a href="http://hexo.io/" target="_blank">Hexo</a>. Theme - <a target="_blank" rel="noopener" href="https://github.com/zthxxx/hexo-theme-Wikitten">wikitten</a>
            
                <br>
                <span id="busuanzi_container_site_pv"><i class="fa fa-eye"></i> <span id="busuanzi_value_site_pv"></span></span>
                &nbsp;|&nbsp;
                <span id="busuanzi_container_site_pv"><i class="fa fa-user"></i> <span id="busuanzi_value_site_uv"></span></span>
            
        </div>
    </div>
</footer>

        

    
        
<script src="/gitee-internal-blog/libs/lightgallery/js/lightgallery.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-thumbnail.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-pager.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-autoplay.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-fullscreen.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-zoom.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-hash.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-share.min.js"></script>

        
<script src="/gitee-internal-blog/libs/lightgallery/js/lg-video.min.js"></script>

    
    
        
<script src="/gitee-internal-blog/libs/justified-gallery/jquery.justifiedGallery.min.js"></script>

    
    
        <script type="text/x-mathjax-config">
    MathJax.Hub.Config({
        tex2jax: {
            inlineMath: [ ["$","$"], ["\\(","\\)"] ],
            skipTags: ['script', 'noscript', 'style', 'textarea', 'pre', 'code'],
            processEscapes: true,
            TeX: {
                equationNumbers: {
                  autoNumber: 'AMS'
                }
            }
        }
    });
    MathJax.Hub.Queue(function() {
        var all = MathJax.Hub.getAllJax();
        for (var i = 0; i < all.length; ++i)
            all[i].SourceElement().parentNode.className += ' has-jax';
    });
</script>
<script async src="//cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.1/MathJax.js?config=TeX-AMS-MML_HTMLorMML"></script>
    



<!-- Custom Scripts -->

<script src="/gitee-internal-blog/js/main.js"></script>


    </div>
</body>
</html>